001// Copyright 2009, 2011 The Apache Software Foundation 002// 003// Licensed under the Apache License, Version 2.0 (the "License"); 004// you may not use this file except in compliance with the License. 005// You may obtain a copy of the License at 006// 007// http://www.apache.org/licenses/LICENSE-2.0 008// 009// Unless required by applicable law or agreed to in writing, software 010// distributed under the License is distributed on an "AS IS" BASIS, 011// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 012// See the License for the specific language governing permissions and 013// limitations under the License. 014 015package org.apache.tapestry5.ioc.internal; 016 017import org.apache.tapestry5.commons.*; 018import org.apache.tapestry5.commons.services.PlasticProxyFactory; 019import org.apache.tapestry5.commons.util.CollectionFactory; 020import org.apache.tapestry5.ioc.ModuleBuilderSource; 021import org.apache.tapestry5.ioc.OperationTracker; 022import org.apache.tapestry5.ioc.ServiceResources; 023import org.apache.tapestry5.ioc.internal.util.InjectionResources; 024import org.apache.tapestry5.ioc.internal.util.InternalUtils; 025import org.slf4j.Logger; 026 027import java.lang.reflect.Method; 028import java.util.Map; 029 030/** 031 * Base class for service decorators and service advisors that work by invoking a module method. 032 * 033 * @since 5.1.0.0 034 */ 035public class AbstractMethodInvokingInstrumenter 036{ 037 private final ModuleBuilderSource moduleSource; 038 039 protected final Map<Class, Object> resourcesDefaults = CollectionFactory.newMap(); 040 041 private final ServiceResources resources; 042 043 private final PlasticProxyFactory proxyFactory; 044 045 protected final Method method; 046 047 protected final Class serviceInterface; 048 049 protected final String serviceId; 050 051 private final Logger logger; 052 053 public AbstractMethodInvokingInstrumenter(ModuleBuilderSource moduleSource, Method method, 054 ServiceResources resources, PlasticProxyFactory proxyFactory) 055 { 056 this.moduleSource = moduleSource; 057 this.method = method; 058 this.resources = resources; 059 this.proxyFactory = proxyFactory; 060 061 serviceId = resources.getServiceId(); 062 063 resourcesDefaults.put(String.class, serviceId); 064 resourcesDefaults.put(ObjectLocator.class, resources); 065 resourcesDefaults.put(ServiceResources.class, resources); 066 logger = resources.getLogger(); 067 resourcesDefaults.put(Logger.class, logger); 068 serviceInterface = resources.getServiceInterface(); 069 resourcesDefaults.put(Class.class, serviceInterface); 070 resourcesDefaults.put(OperationTracker.class, resources.getTracker()); 071 } 072 073 @Override 074 public String toString() 075 { 076 Location location = proxyFactory.getMethodLocation(method); 077 078 return location.toString(); 079 } 080 081 private Object getModuleInstance() 082 { 083 return InternalUtils.isStatic(method) ? null : moduleSource.getModuleBuilder(); 084 } 085 086 protected Object invoke(final InjectionResources injectionResources) 087 { 088 String description = String.format("Invoking method %s", toString()); 089 090 ObjectCreator<Object> plan = InternalUtils.createMethodInvocationPlan(resources.getTracker(), resources, injectionResources, logger, description, getModuleInstance(), method); 091 092 return plan.createObject(); 093 } 094}