Skip to content

Commit d51f4b5

Browse files
committed
SWITCHYARD-1694 Component Service metrics missing from DMR integration
1 parent a7127f4 commit d51f4b5

File tree

16 files changed

+346
-155
lines changed

16 files changed

+346
-155
lines changed

core/admin/src/main/java/org/switchyard/admin/Application.java

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,26 @@ public interface Application {
6161
*/
6262
public ComponentService getComponentService(QName componentServiceName);
6363

64+
/**
65+
* List of implementation and gateway components currently installed in
66+
* SwitchYard runtime.
67+
*
68+
* @return list of SwitchYard components
69+
*/
70+
public List<Component> getComponents();
71+
72+
/**
73+
* Find a component with the specified name.
74+
*
75+
* @param name
76+
* the name of the component.
77+
* @return the component with the specified name; may be null if a component
78+
* with the specified name is not registered with the system.
79+
*/
80+
public Component getComponent(QName name);
81+
82+
83+
6484
/**
6585
* @return the transformers provided by this application
6686
*/

core/admin/src/main/java/org/switchyard/admin/Component.java

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,10 @@
1414

1515
package org.switchyard.admin;
1616

17+
import java.util.List;
1718
import java.util.Map;
18-
import java.util.Set;
19+
20+
import javax.xml.namespace.QName;
1921

2022
/**
2123
* Component
@@ -27,16 +29,32 @@ public interface Component {
2729
/**
2830
* @return the name of this component.
2931
*/
30-
String getName();
32+
QName getName();
3133

3234
/**
3335
* @return supported activation types, e.g. bean, soap, etc.
3436
*/
35-
Set<String> getTypes();
37+
String getType();
3638

3739
/**
3840
* @return component properties.
3941
*/
4042
Map<String,String> getProperties();
4143

44+
/**
45+
* @return the service provided by this component.
46+
*/
47+
ComponentService getService();
48+
49+
/**
50+
* @return the references contained by this component.
51+
*/
52+
List<ComponentReference> getReferences();
53+
54+
/**
55+
* @param componentReferenceName the name of a reference required by
56+
* this component.
57+
* @return the requested reference, may be null
58+
*/
59+
ComponentReference getReference(QName componentReferenceName);
4260
}

core/admin/src/main/java/org/switchyard/admin/SwitchYard.java

Lines changed: 0 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -39,14 +39,6 @@ public interface SwitchYard extends MessageMetricsAware {
3939
*/
4040
List<Application> getApplications();
4141

42-
/**
43-
* List of implementation and gateway components currently installed in
44-
* SwitchYard runtime.
45-
*
46-
* @return list of SwitchYard components
47-
*/
48-
List<Component> getComponents();
49-
5042
/**
5143
* List of services currently registered in the SwitchYard runtime.
5244
*
@@ -61,16 +53,6 @@ public interface SwitchYard extends MessageMetricsAware {
6153
*/
6254
List<Reference> getReferences();
6355

64-
/**
65-
* Find a component with the specified name.
66-
*
67-
* @param name
68-
* the name of the component.
69-
* @return the component with the specified name; may be null if a component
70-
* with the specified name is not registered with the system.
71-
*/
72-
Component getComponent(String name);
73-
7456
/**
7557
* Find an application with the specified name.
7658
*

core/admin/src/main/java/org/switchyard/admin/base/BaseApplication.java

Lines changed: 139 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -16,39 +16,47 @@
1616

1717
import java.util.ArrayList;
1818
import java.util.Collections;
19+
import java.util.EventObject;
1920
import java.util.LinkedHashMap;
2021
import java.util.LinkedList;
2122
import java.util.List;
2223
import java.util.Map;
2324

2425
import javax.xml.namespace.QName;
2526

27+
import org.switchyard.Exchange;
2628
import org.switchyard.admin.Application;
29+
import org.switchyard.admin.Component;
30+
import org.switchyard.admin.ComponentReference;
2731
import org.switchyard.admin.ComponentService;
2832
import org.switchyard.admin.Reference;
2933
import org.switchyard.admin.Service;
3034
import org.switchyard.admin.Transformer;
3135
import org.switchyard.admin.Validator;
3236
import org.switchyard.config.model.composite.ComponentModel;
37+
import org.switchyard.config.model.composite.ComponentReferenceModel;
3338
import org.switchyard.config.model.composite.ComponentServiceModel;
3439
import org.switchyard.config.model.composite.CompositeReferenceModel;
3540
import org.switchyard.config.model.composite.CompositeServiceModel;
3641
import org.switchyard.config.model.composite.InterfaceModel;
3742
import org.switchyard.config.model.property.PropertyModel;
38-
import org.switchyard.config.model.switchyard.EsbInterfaceModel;
3943
import org.switchyard.config.model.switchyard.SwitchYardModel;
4044
import org.switchyard.config.model.transform.TransformModel;
4145
import org.switchyard.config.model.validate.ValidateModel;
46+
import org.switchyard.deploy.ComponentNames;
4247
import org.switchyard.deploy.internal.AbstractDeployment;
48+
import org.switchyard.event.EventObserver;
49+
import org.switchyard.runtime.event.ExchangeCompletionEvent;
4350

4451
/**
4552
* Base implementation of Application.
4653
*/
47-
public class BaseApplication implements Application {
54+
public class BaseApplication implements Application, EventObserver {
4855

4956
private final QName _name;
5057
private Map<QName, Service> _services;
5158
private Map<QName, Reference> _references;
59+
private Map<QName, Component> _components;
5260
private Map<QName, ComponentService> _componentServices;
5361
private List<Transformer> _transformers;
5462
private List<Validator> _validators;
@@ -69,6 +77,15 @@ public BaseApplication(AbstractDeployment deployment) {
6977
addServices();
7078
addReferences();
7179
addProperties();
80+
81+
82+
// register event listener for metrics
83+
_deployment.getDomain().addEventObserver(this, ExchangeCompletionEvent.class);
84+
}
85+
86+
void dispose() {
87+
// remove event listener for metrics
88+
_deployment.getDomain().removeObserver(this);
7289
}
7390

7491
@Override
@@ -129,6 +146,17 @@ public ComponentService getComponentService(QName componentServiceName) {
129146
return _componentServices.get(componentServiceName);
130147
}
131148

149+
@Override
150+
public Component getComponent(QName name) {
151+
return _components.get(name);
152+
}
153+
154+
@Override
155+
public List<Component> getComponents() {
156+
return new ArrayList<Component>(_components.values());
157+
}
158+
159+
132160
@Override
133161
public List<Transformer> getTransformers() {
134162
return Collections.unmodifiableList(_transformers);
@@ -145,6 +173,13 @@ public Map<String, String> getProperties() {
145173
return Collections.unmodifiableMap(_properties);
146174
}
147175

176+
@Override
177+
public void notify(EventObject event) {
178+
if (event instanceof ExchangeCompletionEvent) {
179+
exchangeCompleted((ExchangeCompletionEvent)event);
180+
}
181+
}
182+
148183
/**
149184
* @return the deployment associated with this application.
150185
*/
@@ -195,35 +230,121 @@ private void addValidators() {
195230
}
196231

197232
private void addComponents() {
233+
_components = new LinkedHashMap<QName, Component>();
198234
_componentServices = new LinkedHashMap<QName, ComponentService>();
199235
if (getConfig().getComposite().getComponents() == null) {
200236
return;
201237
}
202-
for (ComponentModel component : getConfig().getComposite().getComponents()) {
203-
// TODO: we need a separate node for components, to support cases
204-
// where the component implements no services. Should also consider
205-
// multiple services per component.
206-
if (component.getServices().size() > 0) {
207-
ComponentServiceModel service = component.getServices().get(0);
208-
if (service.getInterface() == null || EsbInterfaceModel.ESB.equals(service.getInterface().getType())) {
209-
_componentServices.put(service.getQName(), new BaseNoopComponentService(service, component, this));
210-
} else if (InterfaceModel.JAVA.equals(service.getInterface().getType())) {
211-
_componentServices.put(service.getQName(), new BaseJavaComponentService(service, component, this));
212-
} else if (InterfaceModel.WSDL.equals(service.getInterface().getType())) {
213-
_componentServices.put(service.getQName(), new BaseWsdlComponentService(service, component, this));
238+
239+
for (ComponentModel componentConfig : getConfig().getComposite().getComponents()) {
240+
// TODO: Should consider multiple services per component.
241+
final ComponentService service;
242+
if (componentConfig.getServices().size() > 0) {
243+
ComponentServiceModel serviceConfig = componentConfig.getServices().get(0);
244+
if (serviceConfig.getInterface() == null) {
245+
service = new BaseNoopComponentService(serviceConfig, componentConfig, this);
246+
} else if (InterfaceModel.JAVA.equals(serviceConfig.getInterface().getType())) {
247+
service = new BaseJavaComponentService(serviceConfig, componentConfig, this);
248+
} else if (InterfaceModel.WSDL.equals(serviceConfig.getInterface().getType())) {
249+
service = new BaseWsdlComponentService(serviceConfig, componentConfig, this);
250+
} else {
251+
// ESB or unknown
252+
service = new BaseNoopComponentService(serviceConfig, componentConfig, this);
214253
}
254+
_componentServices.put(serviceConfig.getQName(), service);
255+
} else {
256+
service = null;
215257
}
258+
final Map<QName, ComponentReference> references = new LinkedHashMap<QName, ComponentReference>();
259+
if (service == null) {
260+
for (ComponentReferenceModel referenceModel : componentConfig.getReferences()) {
261+
references.put(referenceModel.getQName(), new BaseComponentReference(referenceModel.getQName(),
262+
getInterfaceName(referenceModel.getInterface())));
263+
}
264+
} else {
265+
for (ComponentReference reference : service.getReferences()) {
266+
references.put(reference.getName(), reference);
267+
}
268+
}
269+
final BaseComponent component = new BaseComponent(componentConfig.getQName(),
270+
componentConfig.getImplementation() == null ? "null" : componentConfig.getImplementation()
271+
.getType(), service, references, convertProperties(componentConfig.getProperties()));
272+
_components.put(component.getName(), component);
216273
}
217274
}
218275

219276
private void addProperties() {
220-
_properties = new LinkedHashMap<String, String>();
221277
if (getConfig().getComposite() == null) {
222-
return;
278+
_properties = convertProperties(null);
279+
} else {
280+
_properties = convertProperties(getConfig().getComposite().getProperties());
281+
}
282+
}
283+
284+
private Map<String,String> convertProperties(final Map<String, PropertyModel> properties) {
285+
final Map<String,String> retVal = new LinkedHashMap<String, String>();
286+
if (properties == null) {
287+
return retVal;
223288
}
224-
for (PropertyModel property : getConfig().getComposite().getProperties().values()) {
225-
_properties.put(property.getName(), property.getValue());
289+
for (PropertyModel property : properties.values()) {
290+
retVal.put(property.getName(), property.getValue());
226291
}
292+
return retVal;
293+
}
294+
295+
private String getInterfaceName(InterfaceModel interfaceModel) {
296+
if (interfaceModel == null) {
297+
return null;
298+
}
299+
return interfaceModel.getInterface();
227300
}
228301

302+
void exchangeCompleted(final ExchangeCompletionEvent event) {
303+
// Recording metrics at multiple levels at this point instead of
304+
// aggregating them.
305+
final Exchange exchange = event.getExchange();
306+
final QName qualifiedReferenceName = exchange.getConsumer().getName();
307+
final QName referenceName = ComponentNames.unqualify(qualifiedReferenceName);
308+
final QName componentName = ComponentNames.componentName(qualifiedReferenceName);
309+
if (componentName == null) {
310+
// service gateway initiated exchange
311+
final Service service = _services.get(referenceName);
312+
if (service != null) {
313+
/*
314+
* service also records promoted component service metrics too
315+
* (i.e. producer metrics)
316+
*/
317+
service.recordMetrics(exchange);
318+
}
319+
} else {
320+
// component reference initiated exchange
321+
// 1 - recored service metrics (producer)
322+
final QName serviceName = exchange.getProvider().getName();
323+
final ComponentService service = _componentServices.get(serviceName);
324+
if (service == null) {
325+
// must be routed to composite reference
326+
final Reference reference = _references.get(serviceName);
327+
if (reference != null) {
328+
reference.recordMetrics(exchange);
329+
}
330+
} else {
331+
/*
332+
* XXX: this could throw off metrics for composite services
333+
* since they simply return the metrics for the component
334+
* service they promote. That said, the metrics for the gateways
335+
* will correlate with the global metrics.
336+
*/
337+
service.recordMetrics(exchange);
338+
}
339+
// 2 - record reference metrics (consumer)
340+
final Component component = _components.get(componentName);
341+
if (component != null) {
342+
final ComponentReference reference = component.getReference(referenceName);
343+
if (reference != null) {
344+
reference.recordMetrics(exchange);
345+
}
346+
// else may have been an internal invocation, e.g. orders demo
347+
}
348+
}
349+
}
229350
}

0 commit comments

Comments
 (0)