On 4/14/07, Jean-Sebastien Delfino <[EMAIL PROTECTED]> wrote:

Simon Laws wrote:
> On 4/13/07, Simon Laws <[EMAIL PROTECTED]> wrote:
>>
>>
>>
>> On 4/13/07, Simon Laws <[EMAIL PROTECTED]> wrote:
>> >
>> >
>> >
>> > On 4/12/07, Simon Laws < [EMAIL PROTECTED] > wrote:
>> > >
>> > >
>> > >
>> > > On 4/12/07, Raymond Feng < [EMAIL PROTECTED]> wrote:
>> > > >
>> > > > Hi, Simon.
>> > > >
>> > > > For the composite component, it's probably not necessary to
attach
>> > > > the wire.
>> > > > Can you try to add the following code in DeployerImpl.connect()
to
>> > > > see if it
>> > > > helps?
>> > > >
>> > > > public void connect(Map<SCAObject, Object> models,
>> > > > org.apache.tuscany.assembly.Component definition)
>> > > > throws WiringException {
>> > > >     // Skip the composite
>> > > >     if(definition.getImplementation() instanceof Composite) {
>> > > >         return;
>> > > >     }
>> > > >     // End of skip
>> > > >
>> > > > ...
>> > > > }
>> > > >
>> > > > Thanks,
>> > > > Raymond
>> > > >
>> > > > ----- Original Message -----
>> > > > From: "Simon Laws" < [EMAIL PROTECTED]>
>> > > > To: < [EMAIL PROTECTED]>
>> > > > Sent: Thursday, April 12, 2007 12:19 PM
>> > > > Subject: Re: Composites implementing components problem
>> > > >
>> > > >
>> > > > > On 4/12/07, Simon Laws < [EMAIL PROTECTED]> wrote:
>> > > > >>
>> > > > >>
>> > > > >>
>> > > > >> On 4/12/07, Simon Laws < [EMAIL PROTECTED]> wrote:
>> > > > >> >
>> > > > >> >
>> > > > >> >
>> > > > >> > On 4/12/07, Jean-Sebastien Delfino < [EMAIL PROTECTED]>
>> > > > wrote:
>> > > > >> > >
>> > > > >> > > Simon Laws wrote:
>> > > > >> > > > On 4/12/07, Jean-Sebastien Delfino <
>> [EMAIL PROTECTED]>
>> > > > wrote:
>> > > > >> > > >>
>> > > > >> > > >> Simon Laws wrote:
>> > > > >> > > >> > I'm trying to bring the composite-impl sample up. The
>> > > > sample
>> > > > >> > > >> > uses
>> > > > >> > >
>> > > > >> > > >> nested
>> > > > >> > > >> > composite files and if fails trying to wire up the
>> > > > references
>> > > > >> > > from
>> > > > >> > > >> a top
>> > > > >> > > >> > level component (which is implemented in a separate
>> > > > composite -
>> > > > >> > > see
>> > > > >> > > >> > [1]) to
>> > > > >> > > >> > another component.
>> > > > >> > > >> >
>> > > > >> > > >> > The failure happens during the connect phase of
>> > > > >> > > >> > DeployerImpl.deploy(). Here
>> > > > >> > > >> > it loops round all of the references specified in the
>> > > > model for
>> > > > >> > > the
>> > > > >> > > >> > component in question and then goes to the component
>> > > > >> > > implementation to
>> > > > >> > > >> > get
>> > > > >> > > >> > the reference definition so it can subsequently
>> create a
>> > > > wire.
>> > > > >> > > Here is
>> > > > >> > > >> > the
>> > > > >> > > >> > top of the loop from DeployerImpl.connect() (I added
>> > > > some
>> > > > >> > > comments
>> > > > >> > > >> > here to
>> > > > >> > > >> > highlight the points of interest)
>> > > > >> > > >> >
>> > > > >> > > >> >        // for each  the references specified in the
>> SCDL
>> > > > for the
>> > > > >> > > >> > component
>> > > > >> > > >> >        for (ComponentReference ref :
>> > > > definition.getReferences())
>> > > > >> > > {
>> > > > >> > > >> >            List<Wire> wires = new ArrayList<Wire>();
>> > > > >> > > >> >            String refName = ref.getName();
>> > > > >> > > >> >            // get the definition of the reference
>> which
>> > > > is
>> > > > >> > > described
>> > > > >> > > >> > by the
>> > > > >> > > >> > component implementation
>> > > > >> > > >> >
>> org.apache.tuscany.assembly.ReferencerefDefinition =
>> > > > >> > > >> > getReference(definition.getImplementation (),
>> refName);
>> > > > >> > > >> >            assert refDefinition != null;
>> > > > >> > > >> >
>> > > > >> > > >> > So when it comes to "SourceComponent" [1] it finds
>> that
>> > > > the
>> > > > >> > > >> component is
>> > > > >> > > >> > implemented by another composite. When this
>> information
>> > > > is read
>> > > > >> > > >> into the
>> > > > >> > > >> > model by the CompositeProcessor there is code that
>> > > > specifically
>> > > > >> > > reads
>> > > > >> > > >> the
>> > > > >> > > >> > implementation.composite element, i.e.
>> > > > >> > > >> >
>> > > > >> > > >> >                        } else if
>> > > > >> > > >> > (IMPLEMENTATION_COMPOSITE_QNAME.equals(name)) {
>> > > > >> > > >> >
>> > > > >> > > >> >                            // Read an
>> > > > implementation.composite
>> > > > >> > > >> >                            Composite implementation =
>> > > > >> > > >> > factory.createComposite();
>> > > > >> > > >> >
>> > > > >> > > >> > implementation.setName(getQName(reader,
>> > > > >> > >
>> > > > >> > > >> > NAME));
>> > > > >> > > >> >
>> implementation.setUnresolved
>> > > > (true);
>> > > > >> > > >> >
>> > > > >> > > >> component.setImplementation(implementation);
>> > > > >> > > >> >
>> > > > >> > > >> > Now all this does as far as I can see is create a
>> > > > composite type
>> > > > >> > > with
>> > > > >> > > >> > just
>> > > > >> > > >> > the composite name in it (I assume that the
>> intention is
>> > > > to
>> > > > >> > > resolve
>> > > > >> > > >> this
>> > > > >> > > >> > later on). Hence the connect step fails because the
>> > > > component
>> > > > >> > > >> > implementation
>> > > > >> > > >> > in our example has nothing in it. Specifically it has
>> > > > none of
>> > > > >> > > >> > the
>> > > > >> > > >> > reference
>> > > > >> > > >> > definition information that it would have to look
>> in the
>> > > > other
>> > > > >> > > >> composite
>> > > > >> > > >> > file to get.
>> > > > >> > > >> >
>> > > > >> > > >> > The problem is I'm not sure when this information is
>> > > > intended to
>> > > > >> > > be
>> > > > >> > > >> > linked
>> > > > >> > > >> > up. During the resolve phase when this component
>> > > > implementation
>> > > > >> > > is
>> > > > >> > > >> > reached
>> > > > >> > > >> > the resolver just finds a composite with nothing in
it
>> > > > and, as
>> > > > >> > > far as
>> > > > >> > > >> > I can
>> > > > >> > > >> > tell, just ignores it. How does the system know that
>> > > > this
>> > > > >> > > >> implementation
>> > > > >> > > >> > refers to a composite defined elsewhere rather than
>> just
>> > > >
>> > > > >> > > >> > defining
>> > > > >> > > a
>> > > > >> > > >> > composite with nothing in it?
>> > > > >> > > >> >
>> > > > >> > > >> > I would assume at the resolve or optimize stages this
>> > > > should
>> > > > >> > > happen so
>> > > > >> > > >> > that
>> > > > >> > > >> > we have a complete model when it comes time to
>> build the
>> > > > >> > > >> > runtime.
>> > > > >> > >
>> > > > >> > > >> > Maybe we
>> > > > >> > > >> > need a new type or flag to indicate that this is a
>> > > > composite
>> > > > >> > > >> > implementing a
>> > > > >> > > >> > component.  I'll keep plugging away but if someone
>> could
>> > > > give me
>> > > > >> > > a
>> > > > >> > > >> > pointer
>> > > > >> > > >> > that would be great?
>> > > > >> > > >> >
>> > > > >> > > >> > [1]
>> > > > >> > > >> >
>> > > > >> > > >>
>> > > > >> > >
>>
http://svn.apache.org/repos/asf/incubator/tuscany/java/sca/samples/composite-impl/src/main/resources/OuterComposite.composite
>>
>> > > >
>> > > > >> > > >>
>> > > > >> > > >> >
>> > > > >> > > >> >
>> > > > >> > > >>
>> > > > >> > > >> Simon,
>> > > > >> > > >>
>> > > > >> > > >> This code:
>> > > > >> > > >>                            // Read an
>> > > > implementation.composite
>> > > > >> > > >>                            Composite implementation =
>> > > > >> > > >> factory.createComposite ();
>> > > > >> > > >>
>> > > > >> > > >> implementation.setName(getQName(reader,
>> > > > >> > > >> NAME));
>> > > > >> > > >>
>> implementation.setUnresolved(true);
>> > > > >> > > >>                            component.setImplementation
>> > > > >> > > (implementation);
>> > > > >> > > >> creates a reference to the named composite marked
>> > > > Unresolved.
>> > > > >> > > >>
>> > > > >> > > >> Later in the CompositeProcessor.resolve method, we
>> resolve
>> > > > the
>> > > > >> > > >> Implementations of all the Components in the Composite,
>> > > > including
>> > > > >> > > >> references to other Composites, as follows:
>> > > > >> > > >>        // Resolve component implementations, services
>> and
>> > > > >> > > references
>> > > > >> > > >>         for (Component component:
>> composite.getComponents())
>> > > > {
>> > > > >> > > >>             constrainingType =
>> > > > component.getConstrainingType();
>> > > > >> > > >>             constrainingType = resolver.resolve(
>> > > > >> > > ConstrainingType.class,
>> > > > >> > > >> constrainingType);
>> > > > >> > > >>             component.setConstrainingType
>> > > > (constrainingType);
>> > > > >> > > >>
>> > > > >> > > >>             Implementation implementation =
>> > > > >> > > >> component.getImplementation();
>> > > > >> > > >>             implementation =
>> > > > resolveImplementation(implementation,
>> > > > >> > > >> resolver);
>> > > > >> > > >>             component.setImplementation
(implementation);
>> > > > >> > > >>
>> > > > >> > > >>             resolveContracts(component.getServices(),
>> > > > resolver);
>> > > > >> > > >>             resolveContracts( component.getReferences
(),
>> > > > resolver);
>> > > > >> > > >>         }
>> > > > >> > > >>
>> > > > >> > > >> Hope this helps.
>> > > > >> > > >>
>> > > > >> > > >> --
>> > > > >> > > >> Jean-Sebastien
>> > > > >> > > >>
>> > > > >> > > >>
>> > > > >> > > >>
>> > > > >> > >
>> > > >
>> ---------------------------------------------------------------------
>> > > > >> > > >> To unsubscribe, e-mail:
>> > > > [EMAIL PROTECTED]
>> > > > >> > > >> For additional commands, e-mail:
>> > > > [EMAIL PROTECTED]
>> > > > >> > > >>
>> > > > >> > > >> Thanks Sebastien, That's really helpful. Thanks also
for
>> > > > making
>> > > > >> > > some
>> > > > >> > > >> fixes
>> > > > >> > > > to the SCDL. I'm made some more changes to make the
>> > > > reference names
>> > > > >> > > match
>> > > > >> > > > and I'm now able to get past the problem point in my
mail
>> > > > above.
>> > > > >> > > > Not
>> > > > >> > >
>> > > > >> > > > quite
>> > > > >> > > > there yet but getting further. A question though.
>> > > > >> > > >
>> > > > >> > > > It's still reporting problems with the references in the
>> > > > component
>> > > > >> > > > implementation composite files. This time it is
>> complaining
>> > > > that
>> > > > >> > > > the
>> > > > >> > >
>> > > > >> > > > references don't have enough targets. This is true in
>> their
>> > > >
>> > > > >> > > standalone
>> > > > >> > > > state
>> > > > >> > > > when they are processed as part of the contribution
these
>> > > > >> > > > composites
>> > > > >> > > > don't
>> > > > >> > > > have targets on ther references. This only happens in
the
>> > > > top level
>> > > > >> > > > composite that uses them.
>> > > > >> > > >
>> > > > >> > > > Is this expected behaviour?
>> > > > >> > > >
>> > > > >> > > > Regards
>> > > > >> > > >
>> > > > >> > > > Simon
>> > > > >> > > >
>> > > > >> > >
>> > > > >> > > Interesting :) I think that we currently report a problem
>> > > > when a
>> > > > >> > > reference with multiplicity 1..x  has no target. In your
>> > > > case, if the
>> > > > >> > > reference is promoted, then we shouldn't report a problem
>> > > > right away
>> > > > >> > > when we analyze the composite, as we basically defer any
>> > > > wiring to
>> > > > >> > > the
>> > > > >> > > outer level, i.e. an outer composite containing a
component
>> > > > >> > > implemented
>> > > > >> > > by this composite. So I think we can relax the check in
>> > > > >> > > CompositeUtil.
>> > > > >> > > A
>> > > > >> > > promoted reference with multiplicity 1.x and no targets
>> is OK
>> > > > and
>> > > > >> > > shouldn't be reported as a problem. Its targets will be
>> > > > checked when
>> > > > >> > > we
>> > > > >> > > get to the outer composite.
>> > > > >> > >
>> > > > >> > > Makes sense?
>> > > > >> > >
>> > > > >> > > --
>> > > > >> > > Jean-Sebastien
>> > > > >> > >
>> > > > >> > >
>> > > > >> > >
>> > > >
>> ---------------------------------------------------------------------
>> > > > >> > > To unsubscribe, e-mail:
>> [EMAIL PROTECTED]
>> > > >
>> > > > >> > > For additional commands, e-mail:
>> > > > [EMAIL PROTECTED]
>> > > > >> > >
>> > > > >> > > Sounds like a fine idea to me. How do you know though
>> that a
>> > > > >> > > composite
>> > > > >> > is going to be used later in an outer composite? Do you just
>> > > > record the
>> > > > >> > error as you see it and then remove it later when it the
>> outer
>> > > > >> > composite is
>> > > > >> > processed? I.e. look to see if any component use the
>> composite
>> > > > as an
>> > > > >> > implementation and then go and remove all/selected errors
for
>> > > > the
>> > > > >> > implementing composite.
>> > > > >> >
>> > > > >> > Regards
>> > > > >> >
>> > > > >> > Simon
>> > > > >> >
>> > > > >> Does anyone know why in CompositeCompoentExtension [1] the
>> > > > isCallback
>> > > > >> flag
>> > > > >> is not passed down to binding.createTargetInvoker ? This
causes
>> > > > an NPE on
>> > > > >> the composite-impl test when processing the callback
interfaces
>> > > > because
>> > > > >> createTargetInvoker explicitly tests for it. This is not the
>> only
>> > > > problem
>> > > > >> still left to find but would be interested to know if there
>> is a
>> > > > good
>> > > > >> reason.
>> > > > >>
>> > > > >> Simon
>> > > > >>
>> > > > >> [1]
>> > > > >>
>> > > >
>>
http://svn.apache.org/repos/asf/incubator/tuscany/java/sca/modules/core-spi/src/main/java/org/apache/tuscany/spi/extension/CompositeComponentExtension.java
>>
>> > > > >>
>> > > > >>
>> > > > >
>> > > > > Ok replying to my own email here. I didn't find out the
>> answer to
>> > > > the
>> > > > > previous question but changed the code to let it through the
>> wire
>> > > > creation
>> > > > > piece. I now get a very strange effect. The system throws an
>> > > > unsupported
>> > > > > method exception trying to add the wire back into the component
>> > > > objecy
>> > > > > (CompositeComponentImpl in this case). Sure enough looking at
>> the
>> > > > code you
>> > > > > see
>> > > > >
>> > > > >    public void attachWire(Wire wire) {
>> > > > >        throw new UnsupportedOperationException();
>> > > > >    }
>> > > > >
>> > > > > Now this must have worked at some stage so some configuration
>> must
>> > > > be
>> > > > > wrong
>> > > > > somewhere. I notice that POJOAtomicComponent does implement
>> these
>> > > > methods
>> > > > > but I can't find anything to do with composites that does.
>> > > > AnyhowI'll
>> > > > > invetigate the module activation stuff around the POJO piece
and
>> > > > see how
>> > > > > these get put into the system. Is it just that we need to make
a
>> > > > similar
>> > > > > thing for composite implementations?
>> > > > >
>> > > > > Regards
>> > > > >
>> > > > > Simon
>> > > > >
>> > > >
>> > > >
>> > > >
>> > > >
>> ---------------------------------------------------------------------
>> > > > To unsubscribe, e-mail: [EMAIL PROTECTED]
>> > > > For additional commands, e-mail: [EMAIL PROTECTED]
>> > > >
>> > > > Hi Raymond, Thanks for that. It may very well be that we don't
>> have
>> > > to wire up the composite component because we expect the
>> components in the
>> > > composite that implements the composite component to be wired
>> instead. There
>> > > is a bit of a discontinuity though.
>> > >
>> > > - The inner composite (the composite being used to implement a
>> > > component) does not have a full set of targets for the references
>> that it
>> > > defines. These are not put in place until the composite is used
>> to implement
>> > > a component in the outer composite.
>> > > - The outer composite contains the composite component and the
>> > > information about how this component is wired up. But the composite
>> > > component is not having wires created for it.
>> > >
>> > > I put the change in and the next problem that showed up is that
when
>> > > the components are started after deployment it gets an NPE
>> because the
>> > > component in the inner composite has no wires. This is true
>> because when the
>> > > wires are created the inner composite references have no targets.
>> Somewhere
>> > > we need to make sure that the invocation chain is formed
>> correctly to
>> > > include the components that part of the inner composite.
>> > >
>> > > Anyhow I'm going to sleep now so I'll chase again in the morning.
>> > >
>> > > Regards
>> > >
>> > > Simon
>> > >
>> > So, this is getting a little complicated. As above I don't think we
>> can
>> > ignore the wires that are created in response to the composite
>> components. I
>> > think they should be attached to the appropriate components in the
>> > composites implementing the composite components. However this
>> seems to be a
>> > little tricky. What I've done is traverse the model to find the
>> component
>> > from the inner composite, convert this to the right runtime
>> component and
>> > addthe wire there. Needless to say this doesn't work fully yet.
>> Well it
>> > works for the call out to the java component but the call the
>> composite
>> > component doesn't work. I suspect this is because whatever code
>> attaches the
>> > wire at the target end needs the same treatment. I'mm off to track
>> this down
>> > now:-)
>> >
>> > I suspect the real answer is to fix up the model correctly so that
the
>> > targets are in the right place to start with. Anyone care to comment?
>> >
>> > Simon
>> >
>> >
>> >
>> > So I see a problem with creating the wire to a composite component in
>> that the target invoker is not created properly (well not at all
>> actually).
>> The CompositeComponentImpl.createTargetInvoker() method, i.e. the
method
>> at the target component that creates the invoker has the following
>> logic.
>>
>>     public TargetInvoker createTargetInvoker(String name, Operation
>> operation, boolean isCallback)
>>         throws TargetInvokerCreationException {
>>         Service service = getService(name);
>>         if (service != null) {
>>             if (service.getServiceBindings().isEmpty()) {
>>                 // for now, throw an assertion exception.
>>                 // We will need to choose bindings during allocation
>>                 throw new AssertionError();
>>             }
>>             ServiceBinding binding =
>> service.getServiceBindings().get(0);
>>             return binding.createTargetInvoker(name, operation,
>> isCallback);
>>         }
>>         Reference reference = getReference(name);
>>         if (reference != null) {
>>             if (reference.getReferenceBindings().isEmpty()) {
>>                 // for now, throw an assertion exception.
>>                 // We will need to choose bindings during allocation
>>                 throw new AssertionError();
>>             }
>>             ReferenceBinding binding = reference.getReferenceBindings
>> ().get(0);
>>             binding.createTargetInvoker(name, operation, isCallback);
>>         }
>>         return null;
>>     }
>>
>> In my case the name that is passed in is the name of the reference from
>> the source side to which the wire refers. The name of a reference on
the
>> source side matches neither a service or a reference in the target
>> composite
>> (will it ever?) so a target invoker isn't created. I might expect the
>> name
>> of the target of the reference to match but not the name of the
>> reference
>> itself. Anyhow can't confirm is causing my problem but it looks fishy.
>>
>> The flip side of this is, assuming I am correct that we should be
wiring
>> to the actual component and not the composite component (big
>> assumption),
>> then we shouldn't be asking the composite component to create target
>> invokers.
>>
>> Simon
>>
> OK so I put a copy of the deployer with the changes I had to make to
make
> the composite-impl test mostly work (callbacks still not working as
> callback
> not being injected) up in the sandbox [1]. As I assuming this test
> used to
> work I'm concerned that I'm going in the wrong direction so need someone
> more knowledgeable to check this before I go on.
>
> Thanks
>
> Simon
>
> [1]
>
http://svn.apache.org/repos/asf/incubator/tuscany/sandbox/slaws/DeployerImpl.java
>
>

Simon,

You were going in the right direction! After an unsuccessful attempt to
fix the Deployer.connect() methods to set up wires with LocalBindings, I
picked on the approach that you had started in your copy of Deployer and
was able to get nested composites working again. I actually went a bit
further on the path you had started, instead of navigating the assembly
model to find out the actual connections between promoted references and
target component services and build the runtime wire connections
directly from that, I now do the following:

        for (org.apache.tuscany.assembly.Component component:
composite.getComponents()) {

            // Process composite components
            if (component.getImplementation() instanceof Composite) {
                for (ComponentReference componentReference:
component.getReferences()) {

                    // Process component references with a default binding
                    if (componentReference.getBinding(SCABinding.class)
!= null) {

                        // Wire the promoted references inside the
nested composite
                        CompositeReference compositeReference =
(CompositeReference)componentReference.getReference();
                        if (compositeReference != null) {
                            for (ComponentReference promotedReference:
compositeReference.getPromotedReferences()) {

                                // Add all the actual (promoted) targets
to the promoted reference
                                for (ComponentService componentService:
componentReference.getTargets()) {
                                    org.apache.tuscany.assembly.Service
service = componentService.getService();
                                    if (service instanceof
CompositeService) {
                                        CompositeService
compositeService = (CompositeService)service;
                                        ComponentService promotedService
= compositeService.getPromotedService();
                                        if (promotedService != null) {

promotedReference.getTargets().add(promotedService);
                                        }
                                    } else {

promotedReference.getTargets().add(componentService);
                                    }
                                }
                                promotedReference.promotedAs().clear();
                            }
                        }
                    }
                }
            }
        }

This code basically flattens the wiring graph, by adding the actual
targets to the source promoted references. Then the rest of the deployer
and runtime works exactly the same as before. There are still some
limitations with this approach, so we'll need to spend more time on this
next week to make the algorithm recurse down multiple levels of
composition and also see how we want to handle multiple instances of the
same composite. I'm also not too keen on altering the metadata model
like this, but this seemed to be the simplest way for now to get wiring
to work given the current runtime wiring logic.

Callbacks are also working now. First callbacks were not injected
because of a small bug in the code indexing the callback properties
(needed to index them by callback interface name instead of property
name).

--
Jean-Sebastien


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Thanks for sharing that Sebastien. I don't object to improving the
fidelity of the model. But, as you suggest, would be good to take a step
back and consider the separation of concerns between model and deployed
runtime components, and the role the deployer plays, next week.

I'll go and give the sample a spin:-)

Simon

Reply via email to