geronimo-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Alex Blewitt <Alex.Blew...@ioshq.com>
Subject Re: [General] Container interface and AbstractContainer
Date Thu, 14 Aug 2003 10:51:24 GMT

On Thursday, Aug 14, 2003, at 11:19 Europe/London, Greg Wilkins wrote:

> Alex Blewitt wrote:
>> You just need to be able to read through the configuration using an 
>> Iterator, surely?
>
> Not if you want automatic persistence. Making it a Bean is good.
> but whatever I agree it is a bad idea for this Container.

I don't see that automatic persistence couldn't be achieved using an 
iterator. Instead of JMX -> MBean,  you'd have ConfigurationAgent -> 
Container, or even JMX -> DynamicMBean -> ConfigurationAgent -> 
Container.

>>> So how about the following
>>>
>>>      void addComponent(Component)
>>>      void removeComponent(Component)
>>>      ObjectName[] getComponents()
>> Even worse, IMHO. A container contains components, not JMX 
>> objects/ObjectNames.
>
> getComponents is a conveniance method.  Each Component has
> a JMX ObjectName and a common thing that you will want to do
> on a Container is to find out all the ObjectNames that it contains.

Ah, but a Component is so much more than an ObjectName. Well, a bit 
more, anyway.

The point is that since a Container contains Components, it should 
return a 'thing' of Components. Then, if you want to get to a point 
where you need object names, you can go through each component and ask 
it for its name.

Just returning object names won't give you any extra benefit, and if 
that's all you return, then you won't be able to access any of the 
component methods (which will give you things in addition to the other 
bits).

> > And you've still got the array, which was what I
>> meant in my last e-mail.
>
> Some people like arrays, some people like Collection, others
> prefer iterators.  I can see all sides and am happy eitherway,
> so long as you are consistent.   However - JMX is not very
> Collection friendly, well many JMX agents anyway.  Thus keeping
> to simple types where possible is best.

Only for the layer that talks to the JMX agent. It doesn't need to be 
the end container itself, surely? You can implement the Container 
internally using a Collection, and then provide an MBean that will talk 
to it.

I don't see that (necessarily) JMX Agents not liking Collections is a 
good reason not to use them. I'm sure that some support them now, and a 
growing number will do. However, making things by an array now is 
likely to lead to one of two design decisions being made:

o Use an array internally, because that's what the JMX-friendly-method 
is called
o Use a Collection, and then waste time/space creating an array when 
required

(Mind you, since (hopefully) you're only confguring this once/a few 
times, such a slowdown for the second point is probably worth paying)

>>> But we still don't have a method to iterate over all the
>>> Components, or get them all.  So either we need something like
>>>
>>>     ListIterator getComponentIterator()
>> Why not just Iterator? I don't see the benefit of ListIterator.
>
> Because:
>   + Order and reverse order are important.  You want to stop
>     the components in the reverse order you started them.
>   + Doing some operations like removal via the iterator
>     can also be simpler, more efficient and less prone to
>     simultaneous modification problems.

I don't think that it makes any difference whether you use ListIterator 
instead of Iterator for the remove, surely? They're just methods that 
are processed by the underlying implementation.

I do take your implication that a LinkedList is likely to be easier for 
removals, which would therefore give you a list iterator.

Can you use ListIterator to go from the end? I know it allows you to go 
backwards/forwards, but can you go to the end directly? Or do you have 
to scan through to the end, then work backwards?

In any case, at least there's a good reason to want to use ListIterator 
:-)

>>> OR we just give up on typing and do:
>>>
>>>    interface Container extends Component, Collection
>>>    {
>>>      ObjectName[] getComponents()
>>>    }
>> Urg. No, I don't like that at all. A Container shouldn't implement 
>> Collection -- if it does, it breaks all manner of things (not the 
>> least of which is that you have to add a whole bunch of spurious 
>> methods to a Container implementation to get it to work.
>
> Just running it up the flag pole.  I'm not sure I agree with
> your distinction that a Container is not a Collection... but then
> I'd like it to be typed anyway, so I was not keen on the Collection
> idea.

If it is a collection, then you must provide an 'add' method that takes 
an object. I can then do:

container.add(new Applet())

which is going to bugger up your assumption that the Container only 
contains Components.

The point is, a Container can be implemented in terms of a Collection, 
but it is not a strict Collection as far as the Java API is concerned: 
"A collection represents a group of objects, known as its elements." 
(From JDK Docs). That means if a Container is a collection, I can put 
any object I want in there -- and this is cearly not the case here :-)

>> public interface Container extends Component {
>>   public Iterator getComponents();
>>   public void addComponent(Component component);
>>   public void removeComponent(Component component);
>> }
>
> Make that a ListIterator and I'm 95% happy.

You made good points above re: being ListIterator

> Add the conveniance method for getting an array of ObjectNames
> and I'm 100%

It is very likely that other objects may want to get a bunch of Object 
Names from a collection. It might be better putting it in a utility 
class:

public class 
ConvertCollectionToObjectNameBecauseICantThinkOfAGoodNameAtTheMoment {
   public ObjectName[] getObjectNamesFrom(Collection collection) {
     return getObjectNamesFrom(collection.iterator());
   }
   public ObjectName[] getObjectNamesFrom(Iterator iterator) {
     List results = new LinkedList();
     while(iterator.hasNext()) {
       results.add(((JMXName)it.next()).getObjectName());
     }
     return (ObjectName[]) results.toArray(new ObjectName[0]);
   }
}

public interface JMXName {
   public ObjectName getObjectName();
}

Alex.


Mime
View raw message