001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: *
017: */
018:
019: package org.apache.jmeter.functions;
020:
021: import java.io.Serializable;
022: import java.util.Collection;
023: import java.util.LinkedList;
024: import java.util.List;
025:
026: import org.apache.jmeter.engine.util.CompoundVariable;
027: import org.apache.jmeter.samplers.SampleResult;
028: import org.apache.jmeter.samplers.Sampler;
029: import org.apache.jmeter.threads.JMeterContext;
030: import org.apache.jmeter.threads.JMeterContextService;
031: import org.apache.jmeter.threads.JMeterVariables;
032: import org.apache.jmeter.util.BeanShellInterpreter;
033: import org.apache.jmeter.util.JMeterUtils;
034: import org.apache.jorphan.logging.LoggingManager;
035: import org.apache.log.Logger;
036:
037: /**
038: * A function which understands BeanShell
039: *
040: */
041: public class BeanShell extends AbstractFunction implements Serializable {
042:
043: private static final Logger log = LoggingManager
044: .getLoggerForClass();
045:
046: private static final long serialVersionUID = 1L;
047:
048: private static final List desc = new LinkedList();
049:
050: private static final String KEY = "__BeanShell"; //$NON-NLS-1$
051:
052: public static final String INIT_FILE = "beanshell.function.init"; //$NON-NLS-1$
053:
054: static {
055: desc.add(JMeterUtils.getResString("bsh_function_expression"));// $NON-NLS1$
056: desc.add(JMeterUtils.getResString("function_name_param"));// $NON-NLS1$
057: }
058:
059: transient private Object[] values;
060:
061: transient private BeanShellInterpreter bshInterpreter = null;
062:
063: public BeanShell() {
064: }
065:
066: public Object clone() throws CloneNotSupportedException {
067: return super .clone();
068: }
069:
070: /*
071: * (non-Javadoc)
072: *
073: * @see org.apache.jmeter.functions.Function#execute(SampleResult, Sampler)
074: */
075: public synchronized String execute(SampleResult previousResult,
076: Sampler currentSampler) throws InvalidVariableException {
077:
078: if (bshInterpreter == null) // did we find BeanShell?
079: {
080: throw new InvalidVariableException("BeanShell not found");
081: }
082:
083: JMeterContext jmctx = JMeterContextService.getContext();
084: JMeterVariables vars = jmctx.getVariables();
085:
086: String script = ((CompoundVariable) values[0]).execute();
087: String varName = ""; //$NON-NLS-1$
088: if (values.length > 1) {
089: varName = ((CompoundVariable) values[1]).execute();
090: }
091:
092: String resultStr = ""; //$NON-NLS-1$
093:
094: log.debug("Script=" + script);
095:
096: try {
097:
098: // Pass in some variables
099: if (currentSampler != null) {
100: bshInterpreter.set("Sampler", currentSampler); //$NON-NLS-1$
101: }
102:
103: if (previousResult != null) {
104: bshInterpreter.set("SampleResult", previousResult); //$NON-NLS-1$
105: }
106:
107: // Allow access to context and variables directly
108: bshInterpreter.set("ctx", jmctx); //$NON-NLS-1$
109: bshInterpreter.set("vars", vars); //$NON-NLS-1$
110: bshInterpreter.set(
111: "threadName", Thread.currentThread().getName()); //$NON-NLS-1$
112:
113: // Execute the script
114: Object bshOut = bshInterpreter.eval(script);
115: if (bshOut != null) {
116: resultStr = bshOut.toString();
117: }
118: if (varName.length() > 0) {
119: vars.put(varName, resultStr);
120: }
121: } catch (Exception ex) // Mainly for bsh.EvalError
122: {
123: log.warn("Error running BSH script", ex);
124: }
125:
126: log.debug("Output=" + resultStr);
127: return resultStr;
128:
129: }
130:
131: /*
132: * Helper method for use by scripts
133: *
134: */
135: public void log_info(String s) {
136: log.info(s);
137: }
138:
139: /*
140: * (non-Javadoc)
141: *
142: * @see org.apache.jmeter.functions.Function#setParameters(Collection)
143: */
144: public synchronized void setParameters(Collection parameters)
145: throws InvalidVariableException {
146:
147: values = parameters.toArray();
148:
149: if (values.length < 1 || values.length > 2) {
150: throw new InvalidVariableException(
151: "Expecting 1 or 2 parameters, but found " + values.length);//$NON-NLS-1$
152: }
153:
154: try {
155: bshInterpreter = new BeanShellInterpreter(JMeterUtils
156: .getProperty(INIT_FILE), log);
157: } catch (ClassNotFoundException e) {
158: throw new InvalidVariableException("BeanShell not found");
159: }
160: }
161:
162: /*
163: * (non-Javadoc)
164: *
165: * @see org.apache.jmeter.functions.Function#getReferenceKey()
166: */
167: public String getReferenceKey() {
168: return KEY;
169: }
170:
171: /*
172: * (non-Javadoc)
173: *
174: * @see org.apache.jmeter.functions.Function#getArgumentDesc()
175: */
176: public List getArgumentDesc() {
177: return desc;
178: }
179:
180: }
|