You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tuscany.apache.org by Giorgio Zoppi <gi...@gmail.com> on 2007/11/27 15:27:15 UTC

Callback problem

Hi,
i've a problem with callbacks in this situation.
I create a component, call it.. AComponent


@Remotable
@Callback(AComponentCallback.class)

public interface AComponent {
    @OneWay
void someMethod();
}

public interface AComponentCallback
{
  void receiveResult()
}

I'd like to set callback to AComponent dynamically and i's wiring
target dynamically to a component, is it feasible?
I.e something like:

ServiceReferenceImpl<WorkerService> myworker =
(ServiceReferenceImpl<WorkerService>)workerQueue.get();
ServiceReference<WorkpoolService> workpoolServiceReference =
workpoolContext.createSelfReference(WorkpoolService.class);
myworker.setCallback(workpoolServiceReference);
WorkerService ws = myworker.getService();
ws.compute(new TestJob(10));
	
I tried, but when it computes I got

http://petrus:49233/WorkerComponent527fe31a93f9f21b5378257c5e343047c99445dc
     [java] 27-nov-2007 15.22.50 workpool.WorkerServiceImpl compute
     [java] INFO:
WorkerComponent527fe31a93f9f21b5378257c5e343047c99445dc is computing a
new job
     [java] RuntimeException invoking receiveResult:
org.osoa.sca.ServiceRuntimeException: No callback wire found for /
     [java] org.osoa.sca.ServiceRuntimeException: No callback wire found for /
     [java]     at
org.apache.tuscany.sca.core.invocation.JDKCallbackInvocationHandler.invoke(JDKCallbackInvocationHandler.java:63)

The question is then how are callbacks attached to a component? And
when callbacks are wired?

BTW I saw Apache Tribes for group memebership and it's ok for small groups.

Cheers,
Giorgio.

---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org


Re: Callback problem

Posted by Simon Nash <na...@hursley.ibm.com>.
The error message you are seeing is caused by the callback address not
being set in the "To" message context.  This suggests that the code doing
the invocation is not aware that it is invoking through an interface that
has a callback interface.  However, the code looks OK, as the WorkerService
interface does define a callback interface WorkerServiceCallback.

I am wondering whether the problem is related to this code in
JDKInvocationHandler.handleCallback():
   if (wire.getSource() == null || wire.getSource().getCallbackEndpoint() == null) {
       return;
   }
If the wire to the dynamically generated worker component is returning
null from the wire.getSource().getCallbackEndpoint() call, this would
explain the problem.

   Simon

Simon Nash wrote:

> One more question.  What is the code in the worker that makes a
> callback to the workpool?  Does it use an injected reference
> annotated with @Callback, or does it make the callback using a
> CallableReference for the callback that it obtains from the
> RequestContext using the getCallback() method?
> 
>   Simon
> 
> Simon Nash wrote:
> 
>>
>> Giorgio Zoppi wrote:
>>
>>> 2007/11/27, Simon Nash <na...@hursley.ibm.com>:
>>>
>>>> This should work.  I am trying to understand the code example you
>>>> gave.  In the code snippet you have a call to setCallback() that
>>>> passes a ServiceReference<WorkpoolService> as the callback for a
>>>> service of type WorkpoolService.  However, your sample service is
>>>> of type AComponent and its callback service is of type
>>>> AComponentCallback.  Somewhere you need to call setCallback() on
>>>> a service reference of type AComponent, passing a callback service
>>>> reference of type AComponentCallback.  Is there any code that
>>>> does this?
>>>
>>>
>>>
>>> Let me explain, the example was a proof of concept.
>>> Actually in my code I have a component of name
>>> WorkerComponentdc2c3b13d2aaa45d33c779af064c447f460d89f3, which is
>>> dynamically generated, which it has no reference to other components.
>>> Its definition is given by a template:
>>> private StringTemplate t = new StringTemplate("<component
>>> xmlns=\"http://www.osoa.org/xmlns/sca/1.0\"
>>> name=\"$componentName$\">\n" +
>>>             "<implementation.java class=\"$className$\"/>"+
>>>             "<property name=\"workerName\">$componentName$</property>"+
>>>             "</component>");
>>> I process it with my own component processor and then i add it to the
>>> composite.(replacing $name$, with appropriate values)
>>>
>>> This is my worker.This worker implements an interface:
>>>
>>> @Remotable
>>> @Callback(WorkerServiceCallback.class)
>>> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
>>> public interface WorkerService<T,E> {
>>>     @OneWay
>>>     void compute(Job<T,E> job);
>>>     void start();
>>>     void stop();
>>> }
>>>
>>> Instead WorkpoolService implements WorkerServiceCallback:
>>>
>>> @Remotable
>>> public interface WorkerServiceCallback {
>>>     void receiveResult(Job resultType,  boolean reuse,
>>> ServiceReferenceImpl<WorkerService> serviceReference);
>>> }
>>>
>>> I generate a reference to a given worker component, i pass it as
>>> CallableReference to
>>> another component,
>>>
>>> @Service(WorkpoolService.class)
>>> @Scope("COMPOSITE")
>>> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
>>>
>>>
>>> public class WorkpoolServiceImpl implements WorkpoolService,
>>> WorkerServiceCallback .
>>>
>>>
>> All of this looks OK to me.
>>
>>> Now my requirement is to add dynamically a callback to the worker, but
>>> it fails.So when a callback gets wired to a component?
>>
>>
>>  >
>> I think your code should work.  The callback service reference that
>> you have dynamically set into the service reference for the worker
>> will be passed to the worker on the compute() call.  The worker
>> will store the callback address in a thread-local area and use it
>> when it makes the callback.  Are you by any chance switching threads
>> in the worker and making the callback from a different thread?  This
>> will not work with the current implementation.  I am intending to
>> remove this thread sensitivity but at the moment it is a limitation.
>>
>>   Simon
>>
>>> I have a pair of hypothesis: the first is that a worker needs to set a
>>> callback in its own runtime (in my case i set the callback in the
>>> workpool runtime, which is in another host), the second is that's
>>> something that i don't understand :).
>>>
>>> Cheers,
>>> Giorgio.
>>>
>>> ---------------------------------------------------------------------
>>> To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
>>> For additional commands, e-mail: tuscany-dev-help@ws.apache.org
>>>



---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org


Re: Callback problem

Posted by Simon Nash <na...@hursley.ibm.com>.
One more question.  What is the code in the worker that makes a
callback to the workpool?  Does it use an injected reference
annotated with @Callback, or does it make the callback using a
CallableReference for the callback that it obtains from the
RequestContext using the getCallback() method?

   Simon

Simon Nash wrote:

> 
> Giorgio Zoppi wrote:
> 
>> 2007/11/27, Simon Nash <na...@hursley.ibm.com>:
>>
>>> This should work.  I am trying to understand the code example you
>>> gave.  In the code snippet you have a call to setCallback() that
>>> passes a ServiceReference<WorkpoolService> as the callback for a
>>> service of type WorkpoolService.  However, your sample service is
>>> of type AComponent and its callback service is of type
>>> AComponentCallback.  Somewhere you need to call setCallback() on
>>> a service reference of type AComponent, passing a callback service
>>> reference of type AComponentCallback.  Is there any code that
>>> does this?
>>
>>
>> Let me explain, the example was a proof of concept.
>> Actually in my code I have a component of name
>> WorkerComponentdc2c3b13d2aaa45d33c779af064c447f460d89f3, which is
>> dynamically generated, which it has no reference to other components.
>> Its definition is given by a template:
>> private StringTemplate t = new StringTemplate("<component
>> xmlns=\"http://www.osoa.org/xmlns/sca/1.0\"
>> name=\"$componentName$\">\n" +
>>             "<implementation.java class=\"$className$\"/>"+
>>             "<property name=\"workerName\">$componentName$</property>"+
>>             "</component>");
>> I process it with my own component processor and then i add it to the
>> composite.(replacing $name$, with appropriate values)
>>
>> This is my worker.This worker implements an interface:
>>
>> @Remotable
>> @Callback(WorkerServiceCallback.class)
>> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
>> public interface WorkerService<T,E> {
>>     @OneWay
>>     void compute(Job<T,E> job);
>>     void start();
>>     void stop();
>> }
>>
>> Instead WorkpoolService implements WorkerServiceCallback:
>>
>> @Remotable
>> public interface WorkerServiceCallback {
>>     void receiveResult(Job resultType,  boolean reuse,
>> ServiceReferenceImpl<WorkerService> serviceReference);
>> }
>>
>> I generate a reference to a given worker component, i pass it as
>> CallableReference to
>> another component,
>>
>> @Service(WorkpoolService.class)
>> @Scope("COMPOSITE")
>> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
>>
>>
>> public class WorkpoolServiceImpl implements WorkpoolService,
>> WorkerServiceCallback .
>>
>>
> All of this looks OK to me.
> 
>> Now my requirement is to add dynamically a callback to the worker, but
>> it fails.So when a callback gets wired to a component?
> 
>  >
> I think your code should work.  The callback service reference that
> you have dynamically set into the service reference for the worker
> will be passed to the worker on the compute() call.  The worker
> will store the callback address in a thread-local area and use it
> when it makes the callback.  Are you by any chance switching threads
> in the worker and making the callback from a different thread?  This
> will not work with the current implementation.  I am intending to
> remove this thread sensitivity but at the moment it is a limitation.
> 
>   Simon
> 
>> I have a pair of hypothesis: the first is that a worker needs to set a
>> callback in its own runtime (in my case i set the callback in the
>> workpool runtime, which is in another host), the second is that's
>> something that i don't understand :).
>>
>> Cheers,
>> Giorgio.
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
>> For additional commands, e-mail: tuscany-dev-help@ws.apache.org
>>
>>
>>
> 
> 
> 



---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org


Re: Callback problem

Posted by Simon Nash <na...@hursley.ibm.com>.
Giorgio Zoppi wrote:

> 2007/11/27, Simon Nash <na...@hursley.ibm.com>:
> 
>>This should work.  I am trying to understand the code example you
>>gave.  In the code snippet you have a call to setCallback() that
>>passes a ServiceReference<WorkpoolService> as the callback for a
>>service of type WorkpoolService.  However, your sample service is
>>of type AComponent and its callback service is of type
>>AComponentCallback.  Somewhere you need to call setCallback() on
>>a service reference of type AComponent, passing a callback service
>>reference of type AComponentCallback.  Is there any code that
>>does this?
> 
> Let me explain, the example was a proof of concept.
> Actually in my code I have a component of name
> WorkerComponentdc2c3b13d2aaa45d33c779af064c447f460d89f3, which is
> dynamically generated, which it has no reference to other components.
> Its definition is given by a template:
> private StringTemplate t = new StringTemplate("<component
> xmlns=\"http://www.osoa.org/xmlns/sca/1.0\"
> name=\"$componentName$\">\n" +
> 			"<implementation.java class=\"$className$\"/>"+
> 			"<property name=\"workerName\">$componentName$</property>"+
> 			"</component>");
> I process it with my own component processor and then i add it to the
> composite.(replacing $name$, with appropriate values)
> 
> This is my worker.This worker implements an interface:
> 
> @Remotable
> @Callback(WorkerServiceCallback.class)
> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
> public interface WorkerService<T,E> {
>     @OneWay
>     void compute(Job<T,E> job);
>     void start();
>     void stop();
> }
> 
> Instead WorkpoolService implements WorkerServiceCallback:
> 
> @Remotable
> public interface WorkerServiceCallback {
> 	void receiveResult(Job resultType,  boolean reuse,
> ServiceReferenceImpl<WorkerService> serviceReference);
> }
> 
> I generate a reference to a given worker component, i pass it as
> CallableReference to
> another component,
> 
> @Service(WorkpoolService.class)
> @Scope("COMPOSITE")
> @DataBinding("org.apache.tuscany.sca.databinding.job.Job")
> 
> 
> public class WorkpoolServiceImpl implements WorkpoolService,
> WorkerServiceCallback .
> 
> 
All of this looks OK to me.

> Now my requirement is to add dynamically a callback to the worker, but
> it fails.So when a callback gets wired to a component?
 >
I think your code should work.  The callback service reference that
you have dynamically set into the service reference for the worker
will be passed to the worker on the compute() call.  The worker
will store the callback address in a thread-local area and use it
when it makes the callback.  Are you by any chance switching threads
in the worker and making the callback from a different thread?  This
will not work with the current implementation.  I am intending to
remove this thread sensitivity but at the moment it is a limitation.

   Simon

> I have a pair of hypothesis: the first is that a worker needs to set a
> callback in its own runtime (in my case i set the callback in the
> workpool runtime, which is in another host), the second is that's
> something that i don't understand :).
> 
> Cheers,
> Giorgio.
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
> For additional commands, e-mail: tuscany-dev-help@ws.apache.org
> 
> 
> 



---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org


Re: Callback problem

Posted by Giorgio Zoppi <gi...@gmail.com>.
2007/11/27, Simon Nash <na...@hursley.ibm.com>:
> This should work.  I am trying to understand the code example you
> gave.  In the code snippet you have a call to setCallback() that
> passes a ServiceReference<WorkpoolService> as the callback for a
> service of type WorkpoolService.  However, your sample service is
> of type AComponent and its callback service is of type
> AComponentCallback.  Somewhere you need to call setCallback() on
> a service reference of type AComponent, passing a callback service
> reference of type AComponentCallback.  Is there any code that
> does this?
Let me explain, the example was a proof of concept.
Actually in my code I have a component of name
WorkerComponentdc2c3b13d2aaa45d33c779af064c447f460d89f3, which is
dynamically generated, which it has no reference to other components.
Its definition is given by a template:
private StringTemplate t = new StringTemplate("<component
xmlns=\"http://www.osoa.org/xmlns/sca/1.0\"
name=\"$componentName$\">\n" +
			"<implementation.java class=\"$className$\"/>"+
			"<property name=\"workerName\">$componentName$</property>"+
			"</component>");
I process it with my own component processor and then i add it to the
composite.(replacing $name$, with appropriate values)

This is my worker.This worker implements an interface:

@Remotable
@Callback(WorkerServiceCallback.class)
@DataBinding("org.apache.tuscany.sca.databinding.job.Job")
public interface WorkerService<T,E> {
    @OneWay
    void compute(Job<T,E> job);
    void start();
    void stop();
}

Instead WorkpoolService implements WorkerServiceCallback:

@Remotable
public interface WorkerServiceCallback {
	void receiveResult(Job resultType,  boolean reuse,
ServiceReferenceImpl<WorkerService> serviceReference);
}

I generate a reference to a given worker component, i pass it as
CallableReference to
another component,

@Service(WorkpoolService.class)
@Scope("COMPOSITE")
@DataBinding("org.apache.tuscany.sca.databinding.job.Job")


public class WorkpoolServiceImpl implements WorkpoolService,
WorkerServiceCallback .


Now my requirement is to add dynamically a callback to the worker, but
it fails.So when a callback gets wired to a component?
I have a pair of hypothesis: the first is that a worker needs to set a
callback in its own runtime (in my case i set the callback in the
workpool runtime, which is in another host), the second is that's
something that i don't understand :).

Cheers,
Giorgio.

---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org


Re: Callback problem

Posted by Simon Nash <na...@hursley.ibm.com>.
This should work.  I am trying to understand the code example you
gave.  In the code snippet you have a call to setCallback() that
passes a ServiceReference<WorkpoolService> as the callback for a
service of type WorkpoolService.  However, your sample service is
of type AComponent and its callback service is of type
AComponentCallback.  Somewhere you need to call setCallback() on
a service reference of type AComponent, passing a callback service
reference of type AComponentCallback.  Is there any code that
does this?

   Simon

Giorgio Zoppi wrote:

> Hi,
> i've a problem with callbacks in this situation.
> I create a component, call it.. AComponent
> 
> 
> @Remotable
> @Callback(AComponentCallback.class)
> 
> public interface AComponent {
>     @OneWay
> void someMethod();
> }
> 
> public interface AComponentCallback
> {
>   void receiveResult()
> }
> 
> I'd like to set callback to AComponent dynamically and i's wiring
> target dynamically to a component, is it feasible?
> I.e something like:
> 
> ServiceReferenceImpl<WorkerService> myworker =
> (ServiceReferenceImpl<WorkerService>)workerQueue.get();
> ServiceReference<WorkpoolService> workpoolServiceReference =
> workpoolContext.createSelfReference(WorkpoolService.class);
> myworker.setCallback(workpoolServiceReference);
> WorkerService ws = myworker.getService();
> ws.compute(new TestJob(10));
> 	
> I tried, but when it computes I got
> 
> http://petrus:49233/WorkerComponent527fe31a93f9f21b5378257c5e343047c99445dc
>      [java] 27-nov-2007 15.22.50 workpool.WorkerServiceImpl compute
>      [java] INFO:
> WorkerComponent527fe31a93f9f21b5378257c5e343047c99445dc is computing a
> new job
>      [java] RuntimeException invoking receiveResult:
> org.osoa.sca.ServiceRuntimeException: No callback wire found for /
>      [java] org.osoa.sca.ServiceRuntimeException: No callback wire found for /
>      [java]     at
> org.apache.tuscany.sca.core.invocation.JDKCallbackInvocationHandler.invoke(JDKCallbackInvocationHandler.java:63)
> 
> The question is then how are callbacks attached to a component? And
> when callbacks are wired?
> 
> BTW I saw Apache Tribes for group memebership and it's ok for small groups.
> 
> Cheers,
> Giorgio.
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
> For additional commands, e-mail: tuscany-dev-help@ws.apache.org
> 
> 
> 

-- 
Simon C Nash   IBM Distinguished Engineer
Hursley Park, Winchester, UK   nash@hursley.ibm.com
Tel. +44-1962-815156   Fax +44-1962-818999


---------------------------------------------------------------------
To unsubscribe, e-mail: tuscany-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: tuscany-dev-help@ws.apache.org