001/* 002 * Copyright 2002-2012 the original author or authors. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * https://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package org.springframework.aop.framework; 018 019import java.io.Serializable; 020 021import org.springframework.util.Assert; 022 023/** 024 * Convenience superclass for configuration used in creating proxies, 025 * to ensure that all proxy creators have consistent properties. 026 * 027 * @author Rod Johnson 028 * @author Juergen Hoeller 029 * @see AdvisedSupport 030 */ 031public class ProxyConfig implements Serializable { 032 033 /** use serialVersionUID from Spring 1.2 for interoperability */ 034 private static final long serialVersionUID = -8409359707199703185L; 035 036 037 private boolean proxyTargetClass = false; 038 039 private boolean optimize = false; 040 041 boolean opaque = false; 042 043 boolean exposeProxy = false; 044 045 private boolean frozen = false; 046 047 048 /** 049 * Set whether to proxy the target class directly, instead of just proxying 050 * specific interfaces. Default is "false". 051 * <p>Set this to "true" to force proxying for the TargetSource's exposed 052 * target class. If that target class is an interface, a JDK proxy will be 053 * created for the given interface. If that target class is any other class, 054 * a CGLIB proxy will be created for the given class. 055 * <p>Note: Depending on the configuration of the concrete proxy factory, 056 * the proxy-target-class behavior will also be applied if no interfaces 057 * have been specified (and no interface autodetection is activated). 058 * @see org.springframework.aop.TargetSource#getTargetClass() 059 */ 060 public void setProxyTargetClass(boolean proxyTargetClass) { 061 this.proxyTargetClass = proxyTargetClass; 062 } 063 064 /** 065 * Return whether to proxy the target class directly as well as any interfaces. 066 */ 067 public boolean isProxyTargetClass() { 068 return this.proxyTargetClass; 069 } 070 071 /** 072 * Set whether proxies should perform aggressive optimizations. 073 * The exact meaning of "aggressive optimizations" will differ 074 * between proxies, but there is usually some tradeoff. 075 * Default is "false". 076 * <p>For example, optimization will usually mean that advice changes won't 077 * take effect after a proxy has been created. For this reason, optimization 078 * is disabled by default. An optimize value of "true" may be ignored 079 * if other settings preclude optimization: for example, if "exposeProxy" 080 * is set to "true" and that's not compatible with the optimization. 081 */ 082 public void setOptimize(boolean optimize) { 083 this.optimize = optimize; 084 } 085 086 /** 087 * Return whether proxies should perform aggressive optimizations. 088 */ 089 public boolean isOptimize() { 090 return this.optimize; 091 } 092 093 /** 094 * Set whether proxies created by this configuration should be prevented 095 * from being cast to {@link Advised} to query proxy status. 096 * <p>Default is "false", meaning that any AOP proxy can be cast to 097 * {@link Advised}. 098 */ 099 public void setOpaque(boolean opaque) { 100 this.opaque = opaque; 101 } 102 103 /** 104 * Return whether proxies created by this configuration should be 105 * prevented from being cast to {@link Advised}. 106 */ 107 public boolean isOpaque() { 108 return this.opaque; 109 } 110 111 /** 112 * Set whether the proxy should be exposed by the AOP framework as a 113 * ThreadLocal for retrieval via the AopContext class. This is useful 114 * if an advised object needs to call another advised method on itself. 115 * (If it uses {@code this}, the invocation will not be advised). 116 * <p>Default is "false", in order to avoid unnecessary extra interception. 117 * This means that no guarantees are provided that AopContext access will 118 * work consistently within any method of the advised object. 119 */ 120 public void setExposeProxy(boolean exposeProxy) { 121 this.exposeProxy = exposeProxy; 122 } 123 124 /** 125 * Return whether the AOP proxy will expose the AOP proxy for 126 * each invocation. 127 */ 128 public boolean isExposeProxy() { 129 return this.exposeProxy; 130 } 131 132 /** 133 * Set whether this config should be frozen. 134 * <p>When a config is frozen, no advice changes can be made. This is 135 * useful for optimization, and useful when we don't want callers to 136 * be able to manipulate configuration after casting to Advised. 137 */ 138 public void setFrozen(boolean frozen) { 139 this.frozen = frozen; 140 } 141 142 /** 143 * Return whether the config is frozen, and no advice changes can be made. 144 */ 145 public boolean isFrozen() { 146 return this.frozen; 147 } 148 149 150 /** 151 * Copy configuration from the other config object. 152 * @param other object to copy configuration from 153 */ 154 public void copyFrom(ProxyConfig other) { 155 Assert.notNull(other, "Other ProxyConfig object must not be null"); 156 this.proxyTargetClass = other.proxyTargetClass; 157 this.optimize = other.optimize; 158 this.exposeProxy = other.exposeProxy; 159 this.frozen = other.frozen; 160 this.opaque = other.opaque; 161 } 162 163 @Override 164 public String toString() { 165 StringBuilder sb = new StringBuilder(); 166 sb.append("proxyTargetClass=").append(this.proxyTargetClass).append("; "); 167 sb.append("optimize=").append(this.optimize).append("; "); 168 sb.append("opaque=").append(this.opaque).append("; "); 169 sb.append("exposeProxy=").append(this.exposeProxy).append("; "); 170 sb.append("frozen=").append(this.frozen); 171 return sb.toString(); 172 } 173 174}