JavaBeans

minutetwitterΛογισμικό & κατασκευή λογ/κού

7 Ιουν 2012 (πριν από 5 χρόνια και 3 μήνες)

443 εμφανίσεις

JavaBeans
Seminar Report
Antoniol,Sandro,TIE04
FHNW
Hochschule f¨ur Technik
Studiengang I
Supervisor:
Prof.Dr.Dominik Gruntz
Windisch,April 9,2007
Abstract
This report has been written as a part of the seminar “Enterprise Computing“ as-
signment.The aim of this report is to make a detailed examination of JavaBeans,a
component model in the Java world.After giving a brief overview of what JavaBeans
are and what they can be used for,we will look at the concepts of JavaBeans.This
includes,but is not limited to:properties,events and methods,introspection,long term
persistence,and BeanContexts.Samples are given to facilitate the comprehension of the
topics.To avoid showing only loose code snippets with no or only little relation to each
other,a FontSelector JavaBean will be developed step by step through this report.The
resulting Bean allows selecting conveniently a font and setting the font-size.Image 1
depicts the final product.
Figure 1:
The FontSelector JavaBean
Please note,that this report is target to experienced programmers.Keywords such as
observer pattern,serialization,AWT,Swing and reflection should be known by you.
Seminar Report
Contents
1.Introduction to JavaBeans 4
1.1.Definition of a software component......................
4
1.2.Definition of a builder tool...........................
4
1.3.JavaBeans at a glance.............................
5
1.4.JavaBeans basic rules.............................
6
2.Beans Architecture 6
2.1.Properties....................................
6
2.2.Simple Properties................................
7
2.3.Indexed Properties...............................
7
2.4.Bound Properties................................
8
2.5.Constrained Properties.............................
9
3.Events and Methods 11
3.1.Methods.....................................
12
4.Instrospection 13
4.1.Methods of the BeanInfo class.........................
13
4.1.1.Events..................................
13
4.1.2.Properties................................
13
4.1.3.Method.................................
13
4.2.Personalized Bean information with BeanInfo................
14
5.Persistence 15
5.1.Long-term persistence.............................
15
5.2.Bean Reconstitution..............................
16
6.BeanContext 16
7.The Beans class 17
8.Conclusion 18
9.References 19
A.Sample BeanContext applicaton 20
Sandro Antoniol Page 3/24
Seminar Report
1.Introduction to JavaBeans
To start with I would like to quote a sentence from the official JavaBeans API specifi-
cation,which gives a first definition of what JavaBeans are:
“A JavaBean is a reusable software component that can be manipulated vi-
sually in a builder tool”.
Even though this quote seams to be quite simple,we have to clarify what is meant
by ’software component’ and ’builder tool’ in order to be able to fully understand the
quote’s statement.
1.1.Definition of a software component
Software components are self-contained software units developed according to the motto
“Developed themonce,run and reused themeverywhere”.Or in other words,reusability
is the main concern behind the component model.Software components offer predefined
services other components or applications can make use of.To facilitate the use of
these services components have to adhere to a given specification.As Robert Englander
outlines in his book “Developing JavaBeans” (1997) [2],software components “must
behave in ways that are expected.It’s like a society of software citizens.The citizens
(components) bring functionality,while the society (environment) brings structure and
order.” JavaBeans is one of Sun’s component models.The first specification appeared on
December 1996.As Java runs on various platforms the provision of a platform neutral
component model was one of Sun’s main concerns.JavaBeans offer their services by
exposing properties,events and methods.The features a component exposes can be
manipulated visually in a builder tool.This leads us directly to the next definition.
Namely the one of what a builder tool is.
1.2.Definition of a builder tool
Builder tools allow a developer to work with JavaBeans in a convenient way.By ex-
amining a JavaBean by a process known as Introspection,a builder tool exposes the
discovered features of the JavaBean for visual manipulation.A builder tool maintains
a list of all JavaBeans available.It allows you to compose the Bean into applets,appli-
cation,servlets and composite components (e.g.a JFrame),customize its behavior and
appearance by modifying its properties and connect other components to the event of
the Bean or vice versa.Although the previous sentence might imply that a JavaBean
is a visual component,it has not necessarily to be one,as you will see in the following
section.There are different builder tools available,varying in functionality.The plugin
’Visual Editor’ for Eclipse has a moderate support of JavaBeans compared to NetBeans
Sandro Antoniol Page 4/24
Seminar Report
Figure 2:
NetBean’s provided property sheet to customize the FontSelector
which even allows you to develop an application consisting of JavaBeans without writ-
ing a single line of code (in best case).Figure 2 depicts the property sheet provided by
NetBeans when the FontSelector JavaBean is selected.
1.3.JavaBeans at a glance
JavaBeans can appear in two forms:visual and non visual.The former is more common,
as the majority of JavaBeans are extensions of AWT or Swing components.Some Beans
may be simple GUI elements such as a specialized button or slider.Others may be so-
phisticated visual software components such as a diagram component offering different
ways to present the bounded data.They all have in common that they can be customized
at design time in a builder tool.However,as already mentioned,JavaBeans can also be
non visual yet still be customizable using a builder-tool.They do not have to be derived
from a specific class or interface,albeit it is recommended that they implement the Se-
rializable interface.In respect of the source code there is no real difference noticeable
between a JavaBean and a “normal” Java class.Basically what differs the source code
of a “normal” class from a JavaBean is that the latter adheres to the JavaBeans API
specification in terms of how it is developed.Only the strict adherence to this specifi-
Sandro Antoniol Page 5/24
Seminar Report
cation ensures that builder tools can assist a developer to work with JavaBeans.Thus
for many solutions you can either develop a conventional Java class where you have to
write your own code for setting its properties or you can build a JavaBean which allows
you to set the properties through the builder tool.Eventually both methods result in
code just that in the latter case the builder tool creates the code automatically in the
background according to your selection(s).And as already mentioned in the best case
you do not even have to write a single line of code.
1.4.JavaBeans basic rules
A JavaBean should:

be public

implement the Serializable interface

have a no-arg constructor

be derived from javax.swing.JComponent or java.awt.Component if it is visual
2.Beans Architecture
2.1.Properties
Properties are named public attributes which determine the internal state of a JavaBean
and thus its behavior and appearance.For example,a GUI textfield might have a
property named ’maxlength’ which restricts the number of characters one can insert
into the texfield.There exist four different kinds of properties a JavaBean can expose:

Simple

Indexed

Bound

Constrained
All types of property have in common that they are characterized by a pair of set/get
methods.A getter method is used to read the value of a readable property.Its name
has to start with get,as you will see later on.To update the property’s value a setter
method has to be called.Analog to the getter-method its name has to start with set.If
a property should be read-only the latter method has to be left out.On the other side,
if the property should be write-only no getter-method has to be written.The property’s
name is determined by the name used in the pair of methods.Typically the value of a
Sandro Antoniol Page 6/24
Seminar Report
property is stored in a private instance variable whose name matches the name of the
property.But this is not a requirement.How you name the instance variable used in
conjunction with the property is up to you.
The data type of the property can be a built-in type as well as a custom class or
interface.The following code snippet shows the naming pattern for the discussed set/get
methods:
public
void
set <Propertyname >(<Datatype > param){?}
public
<Datatype > get <Propertyname >(){?}
Changing a property may also lead to other actions.For instance,updating the back-
ground color property of a JavaBean might cause a repainting of the bean with its new
color.
2.2.Simple Properties
As the name suggests,simple properties are the simplest of the four.For our FontSelector
we would like to have a default font size,which will be used as initial font size at runtime.
The following code sample shows how this property is defined:
private
String name = ‘‘FontSelector’’;
public
void
setName(String name){
this
.name = name;
}
public
String getName(){
return
name;
}
If the property’s data-type is boolean the get methods can also be named is<Propertyname>.
We use a boolean variable to define whether the user can make a selection or not.
private
boolean
enabled;
public
void
setEnabled(
boolean
enabled){
this
.enabled = enabled;
}
public
boolean
isEnabled(){
return
enabled;
}
2.3.Indexed Properties
If a simple property can hold an array of value they are no longer called simple but
instead indexed properties.The method’s signature has to be adapted accordingly.An
indexed property may expose set/get methods to read/write one element in the array
(so-called ’index getter/setter’) and/or so-called ’array getter/setter’ which read/write
the entire array.
Sandro Antoniol Page 7/24
Seminar Report
public
PropertyType getPropertyName (
int
position)
//
indexed
getter
public
void
setPropertyName (PropertyType element,
int
position)
//
indexed
setter
public
PropertyType[] getPropertyName ()
//
array
getter
public
void
setPropertyName (PropertyType[] list)
//
array
setter
The indexed methods may throw a java.lang.ArrayIndexOutOfBoundsException run-
time exception in case the requested index is outside the current array bounds.
Our FontSelector bean has a string array of font names a user can choose from.The
code for that looks as following:
private
String[] fonts;
public
void
setFonts(String[] fonts) {
this
.fonts = fonts;
}
public
String[] getFonts() {
return
fonts;
}
public
String getFonts(
int
pos){
return
fonts[pos];}
2.4.Bound Properties
Bound properties notify other components of their changed value.JavaBeans follow
the Observer pattern to do this notification.Properties notifying observers about their
changes are referred to as bound properties,as most observers bind a special behaviour
to property changes.
In order to provide this notification service a JavaBean needs to have the following
two methods:
public
void
addPropertyChangeListener (PropertyChangeListener p) {
changes.addPropertyChangeListener (p);
}
public
void
removePropertyChangeListener (PropertyChangeListener p) {
changes.removePropertyChangeListener (p);
}
PropertyChangeListener is an interface declared in the java.beans package.Ob-
servers which want to be notified of property changes have to implement this interface,
which consists of only one method:
public
interface
PropertyChangeListener
extends
EventListener {
public
void
propertyChange(PropertyChangeEvent e);
}
Even though we could organize the list of observers by ourselves the beans package
offers a class named PropertyChangeSupport which takes over this job for us.Apart
Sandro Antoniol Page 8/24
Seminar Report
from having methods to add/remove listeners it possesses various methods to notify the
registered observers about a changed property.In the code shown above the variable
referring an instance of this support class is named changes.The declaration code for
it looks like this:
private
PropertyChangeSupport changes =
new
PropertyChangeSupport (
this
);
Our FontSelector informs about changes of the currently selected font.Of course it
would be wise to make any property a bound property.However in our case we limit
it to one property in order to keep it simple.As you will see in the code below,firing
a notification requires the information which property has changed,what its old value
was and what its new value is.
private
boolean
bold;
public
void
setBold(
boolean
bold){
if
(
this
.bold!= bold){
boolean
wasBold =
this
.bold;
this
.bold = bold;
boldBtn.setSelected(bold);
//
Notify
PropertyChangeListeners
:
firePropertyChange("bold",wasBold,bold);
}
}
public
boolean
isBold(){
return
bold;
}
At this stage it is important to note that in this example there is only one instance
for all bound properties.Thus an observer can not enroll just for the notification of a
particular property.All enrolled observers are notified of any changed bound properties.
As a result,every observer needs to check on notification whether the property that
changed was the one the observer was expecting or something else.This can be easily
done by using the getPropertyName() method of the PropertyChangeEvent object
which is passed to the observer.
2.5.Constrained Properties
Constrained properties are similar to bound properties.But in addition to the latter,
constrained properties inform observers also about an imminent property change.This
allows an observer to inhibit the change of the property by throwing a
PropertyVetoException,in case the observer does not agree to this change.As the
observers which are able to put a veto on a property change do not necessarily have to
be the same which are notified after the change,a JavaBean which is constrained as well
as bound has to maintain two lists of listeners:a list of PropertyChangeListener and
a list of VetoableChangeListener.
Sandro Antoniol Page 9/24
Seminar Report
private
VetoableChangeSupport vetoes =
new
VetoableChangeSupport (
this
);
public
void
addVetoableChangeListener (VetoableChangeListener v) {
vetoes.addVetoableChangeListener (v);
}
public
void
removeVetoableChangeListener (VetoableChangeListener v) {
vetoes.removeVetoableChangeListener (v);
}
By convention the set method must not handle the exception a vetoed observer threw,
rather it has to be forwarded.Hence the set method has to be declared to throw the
PropertyVetoException exception.private int currentFontSize;
private
int
fontSize = 11;
public
void
setFontSize(
int
newFontSize)
throws
PropertyVetoException {
if
(fontSize!= newFontSize){
//
Notify
VetoableChangeListener
:
fireVetoableChange("fontSize",fontSize,newFontSize);
int
oldFontSize = fontSize;
fontSize = newFontSize;
//
Raise
event
:
(
see
chapter
Events
&
Methods
)
notifyFontSizeChangedListeners(newFontSize);
//
It

s
good
practise
to
be
a
bound
property
as
well
:
firePropertyChange("fontSize",oldFontSize,newFontSize);
}
}
public
int
getFontSize() {
return
fontSize;
}
As shown in the code above the property does not only notify the VetoableChangeListeners
but also the PropertyChangeListeners after the change has been performed.Even
though not beeing required it is recommend by the specification that if a property is
constrained it is also bound.
Sandro Antoniol Page 10/24
Seminar Report
3.Events and Methods
JavaBeans can use events to communicate when something interesting happens.The
event model applied for Beans bases on the delegation-event model of AWT,introduced
in Java 1.1.There are three parts involved in this communication:

EventObject (containing information about the event)

EventListener - (the sink)

An Event Source (the Bean)
The java.util.EventObject class is the basis of all Beans events.Even though a Bean
can use EventObject instances for its events,the design pattern guidelines require that
you create your own event type by subclassing the EventObject class.The introduction
of an event requires the declaration of a new listener interface and a new event object.
Additionally the JavaBean has to supply a series of methods for the registration process.
The new interface,class and the methods have to follow a specific naming pattern,as
listed bellow:
Event object:
<EventName >Event
Event listeners interface:
<EventName >Listener
Registration process methods:
public
synchronized
void
add <EventName >Listener(<EventName >Listener l);
public
synchronized
void
remove <EventName >Listener (<EventName >Listener l);
In the following we create an event FontChanged which will be fired when a user changes
the font size.
import
java.util.EventObject;
public
class
FontSizeChangedEvent
extends
EventObject {
private
int
newFontSize;
public
FontSizeChangedEvent (Object source,
int
newFontSize) {
super
(source);
this
.newFontSize = newFontSize;
}
//
Note
:
how
you
call
the
methods
is
up
to
you
.
public
int
getNewFontSize () {
return
newFontSize;
}
}
public
interface
FontSizeChangedListener
extends
java.util.EventListener {
Sandro Antoniol Page 11/24
Seminar Report
public
void
fontSizeChanged (FontSizeChangedEvent e);
}
//
Code
FontSelector
JavaBean
:
//
Note
,
that
the
code
for
the
property
has
already
been
shown
in
the
property
chapter
//
and
is
just
repeated
at
this
point
for
completion
.
private
LinkedList <FontSizeChangedListener > fontSizeChgListeners =
new
LinkedList <FontSizeChangedListener >();
private
int
fontSize = 11;
public
synchronized
void
addFontSizeChangedListener(FontSizeChangedListener l){
fontSizeChgListeners.add(l);
}
public
synchronized
void
removeFontSizeChangedListener(FontSizeChangedListener l){
fontSizeChgListeners.remove(l);
}
protected
void
notifyFontSizeChangedListeners(
int
newFontSize){
LinkedList <FontSizeChangedListener > listeners =
(LinkedList <FontSizeChangedListener >)fontSizeChgListeners.clone();
for
(FontSizeChangedListener l:listeners)
l.fontSizeChanged(
new
FontSizeChangedEvent(
this
,newFontSize ));
}
//
Constrained
Property
public
void
setFontSize(
int
newFontSize)
throws
PropertyVetoException {
if
(fontSize!= newFontSize){
//
Notify
VetoableChangeListener
:
fireVetoableChange("fontSize",fontSize,newFontSize);
int
oldFontSize = fontSize;
fontSize = newFontSize;
fontSizeSlider.setValue(newFontSize);
//
Raise
event
:
notifyFontSizeChangedListeners(newFontSize);
//
It

s
good
practise
to
be
a
bound
property
as
well
:
firePropertyChange("fontSize",oldFontSize,newFontSize);
}
}
3.1.Methods
Regarding methods there are no special rules for JavaBeans.If a method is public it can
be called from other components and it even allows a JavaBean to become a listener of
other Beans’ event(s) provided it implements the appropriate interface.
Sandro Antoniol Page 12/24
Seminar Report
4.Instrospection
As described in the introduction,builder tools typically provide a property sheet where
one can conveniently set the properties of a JavaBean component or connect event listen-
ers to an exposed event.In order to provide this service a builder tool needs to examine
the component for its features (=properties,events and methods).This process is re-
ferred to as “introspection”.To obtain information about a specific JavaBean one can
use the static getBeanInfo() method of the Introspector class.This method returns
an instance of the BeanInfo class,which describes all features a JavaBean exposes.The
use of this method is shown in the following code fragment:
FontSelector fs =
new
FontSelector ();
BeanInfo bi = Introspector.getBeanInfo (fs.getClass ());
The most important methods of the BeanInfo object will now be described in the fol-
lowing sections.
4.1.Methods of the BeanInfo class
4.1.1.Events
To determine what events a JavaBean can fire,the BeanInfo object provides the method
getEventSetDescriptors which returns an array of EventSetDescriptors.As the
name suggests an EventSetDescriptor is a class describing an event.In our example
we use the getName() method to display the name of the events.
EventSetDescriptor[] esd = bi.getEventSetDescriptors ();
for
(
int
i=0;i<esd.length;i++){
System.out.print (esd[i].getName() +"");
}
4.1.2.Properties
The determination of properties works similar to the event determination.The method
getPropertyDescriptors() returns an array of PropertyDescriptors reporting all
properties of a Bean.
PropertyDescriptor pd[] = bi.getPropertyDescriptors ();
for
(
int
i=0;i<pd.length;i++)
System.out.print (pd[i].getName() +"");
4.1.3.Method
It’s no surprise that the methods determination works the same way just with different
names.Note,that only public methods of the Bean will be reported.For each method
Sandro Antoniol Page 13/24
Seminar Report
descriptor,the parameters types for the described methods can be discovered through
the getParameterDescriptors() method.
MethodDescriptor md[] = bi.getMethodDescriptors ();
for
(
int
i=0;i<md.length;i++)
System.out.print (md[i].getName() +"");
4.2.Personalized Bean information with BeanInfo
By default an Introspector uses the Reflection API to determine the features of a
JavaBean.However,a JavaBean can provide its own BeanInfo which will be used
instead by the Introspector to determine the discussed information.This allows a
developer hiding specific properties,events and methods from a builder tool or from
any other tool which uses the Introspector class.Moreover it allows supplying further
details about events/properties/methods as you are in charge of creating the descriptor
objects.Hence you can,for example,call the setShortDescription() method to set a
descriptive description.A BeanInfo class has to be derived from the SimpleBeanInfo
class and its name has to start with the name of the associated JavaBean.At this
point it has to be underlined that the name of the BeanInfo class is the only relation
between a JavaBean and its BeanInfo class.If in the example below the class was named
FontSelector_BeanInfo (note the underline) the Introspector would not recognize
the class as BeanInfo class of the FontSelector JavaBean.
import
java.beans.*;
public
class
FontSelectorBeanInfo
extends
SimpleBeanInfo {
private
final
static
Class beanClass = FontSelector.
class
;
public
PropertyDescriptor[] getPropertyDescriptors() {
PropertyDescriptor[] properties =
new
PropertyDescriptor [3];
try
{
properties[0] =
new
PropertyDescriptor ("fontSize",FontSelector.
class
);
properties [0].setConstrained(Boolean.TRUE);
properties [0].setDisplayName ("Fontsize");
properties[1] =
new
PropertyDescriptor ("bold",FontSelector.
class
);
properties [1].setBound(Boolean.TRUE);
properties [1].setDisplayName ("Bold");
properties[2] =
new
PropertyDescriptor ("fonts",FontSelector.
class
);
properties [2].setDisplayName ("Fonts");
properties [2].setShortDescription("List of fonts one can choose from");
}
catch
(IntrospectionException e) {
e.printStackTrace ();
}
return
properties;
}
}
Sandro Antoniol Page 14/24
Seminar Report
5.Persistence
“Persistence is the ability of an object to store its state.” [5] JavaBeans use the Java
Serialization API to gain this ability.The simplest way to enable serialization of a Bean
is by implementing the Serializable interface.The points you have to consider when
declaring a Bean to be serializable are the same as for any other serializable object (e.g.
how to deal with transient and static variables,whether a validation is required upon
deserialization etc.).The greatest strength of persistence regarding JavaBeans lies in
the ability to create prototypes a new JavaBean can be instantiated from.For example,
a Java application using our FontSelector Bean can serialize the Bean on a Microsoft
Windows machine,the serialized file can be sent to a Linux machine,where another Java
application can instantiate a new Bean with the exact state (same fonts,fontsize etc.)
its counterpart had on the Windows machine.Although serialization is a convenient way
to persist a JavaBean this method has a downside.Serialization is intended to persist an
object for a short time,for example to transfer the object to a remote machine through
Java RMI (Remote Machine Invocation).But JavaBeans are typically persisted to serve
as a prototype that requires a mechanism for long-term persistence.The solution is to
represent the JavaBean in a XML structure,which is topic of the next section.
5.1.Long-term persistence
The beans package supplies the XMLEncoder class,which enables JavaBeans to be saved
in XML format.The use of the XMLEncoder is pretty straightforward.The following
code fragment illustrates how to generate a XML file representing a FontSelector class
instance with its internal state.
FontSelector fs =
new
FontSelector ();
fs.setFontSize (14);
fs.setFonts(
new
String[] {"Arial","Verdana","Times"});
XMLEncoder encoder =
new
XMLEncoder(
new
BufferedOutputStream(
new
FileOutputStream("FontSelector.xml") ) );
encoder.writeObject( fs );
encoder.close();
The resulting XML file looks as follows:
<?xml version="1.0"encoding="UTF -8"?>
<java version="1.6.0"
class
="java.beans.XMLDecoder">
<object
class
="ch.fhnw.ec.fontselector.FontSelector">
<
void
property="fontSize">
<
int
>14</
int
>
</
void
>
<
void
property="fonts">
<array
class
="java.lang.String"length="3">
Sandro Antoniol Page 15/24
Seminar Report
<
void
index="0">
<string >Arial </string >
</
void
>
<
void
index="1">
<string >Verdana </string >
</
void
>
<
void
index="2">
<string >Times </string >
</
void
>
</array >
</
void
>
</object >
</java >
5.2.Bean Reconstitution
A JavaBean is reconstituted from its serialized state by deserialization.This can be
either done in conventional fashion by using a ObjectInputStream object or by using
the static java.beans.Beans.instantiate() method,which most builder tools make
use of.This method looks for a file named ¡Classname¿.ser.If such a file exists the class
is deserialized and returned.Otherwise,the Bean will be created by using the default
no-arg constructor of the class.
FontSelector fs = (FontSelector)Beans.instantiate(
null
,"FontSelector");
However,this method can not be used if a bean has been stored in XML format.In this
case the XMLDecoder class has to be used for reading the XML file and returning the
reconstituted object.
XMLDecoder decoder =
new
XMLDecoder(
new
BufferedInputStream(
new
FileInputStream("FontSelector.xml") ) );
FontSelector fs = (FontSelector)decoder.readObject();
decoder.close();
6.BeanContext
A set of related JavaBeans can be logically grouped into a “context”.This context can
be thought of as a “containing environment” and is known as BeanContext.As stated in
Sun’s tutorial about using the BeanContext API,there are two distinct types of Bean-
Contexts:one which supports membership only (interface
java.beans.beancontext.BeanContext) and one which supports membership and of-
fers services (interface java.beans.beancontext.BeanContextServices) to its Jav-
aBeans nested within.BeanContexts follow the Composite Pattern,where BeanContext
classes are the composite.Thus a BeanContext can not only host JavaBeans but also
BeanContext objects.
Sandro Antoniol Page 16/24
Seminar Report
For each interface the BeanContext API offers a helper class with the basic BeanContext
and the BeanContextServices functionality respectively.For the BeanContext inter-
face the helper class is called BeanContextSupport and for the BeanContextServices
interface BeanContextServicesSupport.
As both classes implement the Collection interface,they can be handled like a col-
lection in terms of adding,removing and retrieving JavaBeans.In case a JavaBean
wishes to obtain a reference to its context when being added to the context it shall
implement the BeanContextChild interface.
In the following we focus on the BeanContextServicesSupport class.As already men-
tioned this class offers services to its hosted beans.The services are supplied by so called
service providers,which can be registered with the context via the context’s addService()
method.JavaBeans that implement the
java.beans.beancontext.BeanContextServicesListener interface and have been reg-
istered as a BeanContextServicesListener will be notified of new added services.
JavaBeans can query the context they are residing in for a list of available services
(getCurrentServiceClasses() ),or ask for a specific service by name using the
getService() method.In a hierarchy of contexts a service request will be forwarded
to the parent context if the request can not be fulfilled.A registered service can also be
removed from a context via the context’s removeService() method.
In Appendix A an example application illustrates the use of the BeanContext function-
ality.The example has been taken from Sun’s JavaBean Tutorial and has no relation to
the FontSelector JavaBean which has been referred to in other code fragments shown in
this report.
7.The Beans class
The Beans class found in java.beans is not meant to be instantiated.It consists of a few
static methods,the most interesting of them (from my point of view) will be outlined in
the following.The instantiate() method has already been mentioned in chapter 5.2.
As its name suggests,the method isDesignTime() informs about whether a JavaBean
is running at design-time,viz,running inside an application builder environment.Using
this method allows a JavaBean,for example,having different appearances at design- and
run-time.The setDesignTime() method is used to set the environment a JavaBean is
running in.Similarly,setGuiAvailable() and isGuiAvailable() sets and informs
whether a GUI is available (depends on the Java Virtual Machine).
Sandro Antoniol Page 17/24
Seminar Report
8.Conclusion
This report addressed various aspects of the development of JavaBeans.We introduced
the termof software components and got to knowwhat JavaBeans are and what their aim
is.We got acquainted with the JavaBean specification API and learned how to obtain
information about a JavaBean and how we can influence this information.Moreover
we examined the methods to persist a JavaBean,described the BeanContexts and some
methods of the Beans class.However,as already announced in the abstract,not all
aspects could be covered in this report.The interested reader is kindly referred to Sun’s
JavaBeans Tutorial for more information,for example,about how to provide a dialog
for customizing a JavaBean (referred to as “Bean Customization”).The tutorial can be
found at:http://java.sun.com/docs/books/tutorial/javabeans
Sandro Antoniol Page 18/24
Seminar Report
9.References
[1]
Cervantes,H.(2002).The JavaBeans Component Model
Retrieved March 30,2007,from
http://www.humbertocervantes.net/beansdiscussion.html
[2]
Englander,R.(1997).Developing Java Beans
Retrieved March 30,2007,from
http://www.oreilly.com/catalog/javabeans/chapter/ch01.html
[3]
Prof.Dr.Ostermann,K.;Dipl.-Inform.Aracic,I.;Dipl.-Inform.Kloppenburg,S.
(2006).Introduction to JavaBeans Component Model
Retrieved April 1,2007,from
http://www.st.informatik.tu-darmstadt.de/pages/lectures/sct/ss06/lectures/V2
JavaBeans.pdf
[4]
MageLang Institute.(1997).JavaBeans Short Course:Introduction to JavaBeans
Retrieved March 24,2007,from
http://java.sun.com/developer/onlineTraining/Beans/JBShortCourse/beans.html
[5]
Sun.(2006).JavaBeans(TM) (The Java
TM
Tutorials)
Retrieved March 24,2007,from
http://java.sun.com/docs/books/tutorial/javabeans
Sandro Antoniol Page 19/24
Seminar Report
A.Sample BeanContext applicaton
On the next page an example application illustrates the use of the BeanContext environ-
ment.The example has been taken from Sun’s JavaBean Tutorial and has no relation
to the FontSelector JavaBean which has been referred to in other code fragments shown
in this report.“The application uses a word counting service to count the number of
words in a given text file”.[5]
Sandro Antoniol Page 20/24
A Word Counting Service Example
The classes defined in this sample application are:

DocumentBean.java

: A JavaBean that encapsulates a
File
object. Create an instance of

this bean by passing it a
String
indicating the name of the text file to represent. This bean

extends
BeanContextChildSupport
, which allows it to listen for addition/revocation of

services in its context. When the bean detects that a
WordCount
service has been added to the

context, it requests the service to count the number of words it contains.

WordCountServiceProvider.java

: A class that acts as the factory for delivering the

WordCount
service. This class implements the
BeanContextServiceProvider

interface.

WordCount.java

: This interface defines the service itself.

DocumentTester.java

: The main test program.
File:
DocumentBean.java
import java.beans.beancontext.*;
import java.io.*;
import java.util.*;
/**
* A JavaBean that encapsulates a text file. When added to a bean context,
* this bean listens for a WordCount service to become available. When
* the service does become available, the DocumentBean requests an
* instance of the service. The service then counts the number of words in the

file,
* and prints a report to standard output.
*/
public final class DocumentBean extends BeanContextChildSupport {
private File document;
private BeanContextServices context;
/**
* Creates a new DocumentBean given the name of the file to read from.
* @param fileName the name of the file to read from
*/
public DocumentBean(String fileName) {
document = new File(fileName);
}
/**
* Called when this bean detects that a new service
* has been registered with its context.
*
* @param bcsae the BeanContextServiceAvailableEvent
*/
public void serviceAvailable(BeanContextServiceAvailableEvent bcsae) {
System.out.println("[Detected a service being added to the context]");
// Get a reference to the context
BeanContextServices context = bcsae.getSourceAsBeanContextServices();
System.out.println("Is the context offering a WordCount service? "
+ context.hasService(WordCount.class));
// Use the service, if it's available
if (context.hasService(WordCount.class)) {
System.out.println("Attempting to use the service...");
try {
WordCount service = (WordCount)context.getService(this, this,
WordCount.class,

document, this);
System.out.println("Got the service!");
service.countWords();
} catch(Exception e) { }
Seminar Report
Sandro Antoniol Page 21/24
}
}
/**
* Called when this bean detects that a service
* has been revoked from the context.
*
* @param bcsre the BeanContextServiceRevokedEvent
*/
public void serviceRevoked(BeanContextServiceRevokedEvent bcsre) {
System.out.println("[Detected a service being revoked from the

context]");
}
}
File:
WordCountServiceProvider.java
import java.beans.beancontext.*;
import java.util.*;
import java.io.*;
/**
* This class is the factory that delivers a word counting service.
* The 3 methods defined in this class are the concrete implementations
* of the BeanContextServiceProvider interface. For this demonstration, the

primary
* method of interest is getService(). The getService() methods returns a new
* WordCount instance. It is called by the bean context when a nested
* JavaBean requests the service.
*/
public final class WordCountServiceProvider implements BeanContextServiceProvider

{
public Object getService(BeanContextServices bcs,
Object requestor,
Class serviceClass,
Object serviceSelector) {
// For this demo, we know that the cast from serviceSelector
// to File will always work.
final File document = (File)serviceSelector;
/* Return an instance of the service. The service itself is
* the WordCount interface, which is implemented here using
* an anonymous inner class.
*/
return new WordCount() {
public void countWords() {
try {
// Create a Reader to the DocumentBean's File
BufferedReader br = new BufferedReader(new

FileReader(document));
String line = null;
int wordCount = 0;
while ((line = br.readLine()) != null) {
StringTokenizer st = new StringTokenizer(line);
while (st.hasMoreTokens()) {
System.out.println("Word " + (++wordCount)
+ " is: " + st.nextToken());
}
}
System.out.println("Total number of words in the document: "
+ wordCount);
System.out.println("[WordCount service brought to you by

WordCountServiceProvider]");
br.close();
} catch(Exception e) { }
}
};
}
Seminar Report
Sandro Antoniol Page 22/24
public void releaseService(BeanContextServices bcs,
Object requestor,
Object service) {
// do nothing
}
public Iterator getCurrentServiceSelectors(BeanContextServices bcs, Class

serviceClass) {
return null; // do nothing
}
}
File:
WordCount.java
/**
* The WordCount service. Implementations of the
* countWords() method are provided by the
* WordCountServiceProvider class.
*/
public interface WordCount {
/**
* Counts the number of words in the file.
*/
public abstract void countWords();
}
File:
DocumentTester.java
import java.beans.beancontext.*;
import java.util.*;
/**
* A test program that creates all of the objects,
* a tests the service capabilities. Run this program
* from the command line using java DocumentTester
*/
public class DocumentTester {
public static void main(String[] args) {
BeanContextServicesSupport context = new BeanContextServicesSupport();

// a bean context
DocumentBean doc1 = new DocumentBean("Test.txt");
context.add(doc1);
context.addBeanContextServicesListener(doc1); // listen for new

services
WordCountServiceProvider provider = new WordCountServiceProvider();
context.addService(WordCount.class, provider); // add the service to

the context
}
}
File:
Test.txt
This text will be analyzed

by the WordCount
service.
Output:
[Detected a service being added to the context]
Is the context offering a WordCount service? true
Attempting to use the service...
Got the service!
Word 1 is: This
Word 2 is: text
Word 3 is: will
Seminar Report
Sandro Antoniol Page 23/24
Word 4 is: be
Word 5 is: analyzed
Word 6 is: by
Word 7 is: the
Word 8 is: WordCount
Word 9 is: service.
Total number of words in the document: 9
[WordCount service brought to you by WordCountServiceProvider]
Seminar Report
Sandro Antoniol Page 24/24