View | Details | Raw Unified | Return to bug 59609
Collapse All | Expand All

(-)a/src/components/org/apache/jmeter/extractor/json/jsonpath/JSONPostProcessor.java (-16 / +28 lines)
Lines 21-26 package org.apache.jmeter.extractor.json.jsonpath; Link Here
21
import java.io.Serializable;
21
import java.io.Serializable;
22
import java.util.Arrays;
22
import java.util.Arrays;
23
import java.util.List;
23
import java.util.List;
24
import java.util.Map;
25
26
import net.minidev.json.JSONObject;
24
27
25
import org.apache.jmeter.processor.PostProcessor;
28
import org.apache.jmeter.processor.PostProcessor;
26
import org.apache.jmeter.samplers.SampleResult;
29
import org.apache.jmeter.samplers.SampleResult;
Lines 125-135 public class JSONPostProcessor extends AbstractScopedTestElement implements Seri Link Here
125
                                        new StringBuilder(getComputeConcatenation()
128
                                        new StringBuilder(getComputeConcatenation()
126
                                                ? extractedValues.size() * 20
129
                                                ? extractedValues.size() * 20
127
                                                : 1);
130
                                                : 1);
128
                                for (Object stringExtracted : extractedValues) {
131
                                for (Object extractedObject : extractedValues) {
129
                                    vars.put(currentRefName + "_" + index, 
132
                                    String extractedString = stringifyJSONObject(extractedObject);
130
                                            stringExtracted != null ? stringExtracted.toString() : ""); //$NON-NLS-1$
133
                                    vars.put(currentRefName + "_" + index,
134
                                            extractedString); //$NON-NLS-1$
131
                                    if (getComputeConcatenation()) {
135
                                    if (getComputeConcatenation()) {
132
                                        concat.append(stringExtracted)
136
                                        concat.append(extractedString)
133
                                                .append(JSONPostProcessor.JSON_CONCATENATION_SEPARATOR);
137
                                                .append(JSONPostProcessor.JSON_CONCATENATION_SEPARATOR);
134
                                    }
138
                                    }
135
                                    index++;
139
                                    index++;
Lines 141-149 public class JSONPostProcessor extends AbstractScopedTestElement implements Seri Link Here
141
                            } else if (matchNumber == 0) {
145
                            } else if (matchNumber == 0) {
142
                                // Random extraction
146
                                // Random extraction
143
                                int matchSize = extractedValues.size();
147
                                int matchSize = extractedValues.size();
144
                                Object obj = extractedValues.get(JMeterUtils.getRandomInt(matchSize));
148
                                int matchNr = JMeterUtils.getRandomInt(matchSize);
145
                                vars.put(currentRefName, 
149
                                placeObjectIntoVars(vars, currentRefName,
146
                                        obj != null ? obj.toString() : ""); //$NON-NLS-1$
150
                                        extractedValues, matchNr);
147
                            } else {
151
                            } else {
148
                                // extract at position
152
                                // extract at position
149
                                if (matchNumber > extractedValues.size()) {
153
                                if (matchNumber > extractedValues.size()) {
Lines 155-174 public class JSONPostProcessor extends AbstractScopedTestElement implements Seri Link Here
155
                                    }
159
                                    }
156
                                    vars.put(currentRefName, defaultValues[i]);
160
                                    vars.put(currentRefName, defaultValues[i]);
157
                                } else {
161
                                } else {
158
                                    Object obj = extractedValues.get(matchNumber - 1);
162
                                    placeObjectIntoVars(vars, currentRefName, extractedValues, matchNumber - 1);
159
                                    vars.put(currentRefName, 
160
                                            obj != null ? obj.toString() : ""); //$NON-NLS-1$
161
                                }
163
                                }
162
                            }
164
                            }
163
                        } else {
165
                        } else {
164
                            // else just one value extracted
166
                            // else just one value extracted
165
                            Object obj = extractedValues.get(0);
167
                            placeObjectIntoVars(vars, currentRefName, extractedValues, 0);
166
                            String objAsString = 
167
                                    obj != null ? obj.toString() : ""; //$NON-NLS-1$
168
                            vars.put(currentRefName, 
169
                                    objAsString); 
170
                            if (matchNumber < 0 && getComputeConcatenation()) {
168
                            if (matchNumber < 0 && getComputeConcatenation()) {
171
                                vars.put(currentRefName + ALL_SUFFIX, objAsString);
169
                                vars.put(currentRefName + ALL_SUFFIX, vars.get(currentRefName));
172
                            }
170
                            }
173
                        }
171
                        }
174
                        vars.put(currentRefName + REF_MATCH_NR, Integer.toString(extractedValues.size()));
172
                        vars.put(currentRefName + REF_MATCH_NR, Integer.toString(extractedValues.size()));
Lines 187-192 public class JSONPostProcessor extends AbstractScopedTestElement implements Seri Link Here
187
        }
185
        }
188
    }
186
    }
189
187
188
    private void placeObjectIntoVars(JMeterVariables vars, String currentRefName,
189
            List<Object> extractedValues, int matchNr) {
190
        vars.put(currentRefName,
191
                stringifyJSONObject(extractedValues.get(matchNr)));
192
    }
193
194
    @SuppressWarnings("unchecked")
195
    private String stringifyJSONObject(Object obj) {
196
        if (obj instanceof Map) {
197
            return new JSONObject((Map<String, ?>) obj).toJSONString();
198
        }
199
        return obj == null ? "" : obj.toString(); //$NON-NLS-1$
200
    }
201
190
    public String getJsonPathExpressions() {
202
    public String getJsonPathExpressions() {
191
        return getPropertyAsString(JSON_PATH_EXPRESSIONS);
203
        return getPropertyAsString(JSON_PATH_EXPRESSIONS);
192
    }
204
    }
(-)a/test/src/org/apache/jmeter/extractor/TestJSONPostProcessor.java (+123 lines)
Line 0 Link Here
1
/*
2
 * Licensed to the Apache Software Foundation (ASF) under one or more
3
 * contributor license agreements.  See the NOTICE file distributed with
4
 * this work for additional information regarding copyright ownership.
5
 * The ASF licenses this file to You under the Apache License, Version 2.0
6
 * (the "License"); you may not use this file except in compliance with
7
 * the License.  You may obtain a copy of the License at
8
 *
9
 *   http://www.apache.org/licenses/LICENSE-2.0
10
 *
11
 * Unless required by applicable law or agreed to in writing, software
12
 * distributed under the License is distributed on an "AS IS" BASIS,
13
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
 * See the License for the specific language governing permissions and
15
 * limitations under the License.
16
 * 
17
 */
18
19
package org.apache.jmeter.extractor;
20
21
import java.nio.charset.StandardCharsets;
22
23
import net.minidev.json.parser.JSONParser;
24
import net.minidev.json.parser.ParseException;
25
26
import org.apache.jmeter.extractor.json.jsonpath.JSONPostProcessor;
27
import org.apache.jmeter.samplers.SampleResult;
28
import org.apache.jmeter.threads.JMeterContext;
29
import org.apache.jmeter.threads.JMeterContextService;
30
import org.apache.jmeter.threads.JMeterVariables;
31
import org.junit.Assert;
32
import org.junit.Test;
33
34
public class TestJSONPostProcessor {
35
36
    private static final String VAR_NAME = "varName";
37
38
    @Test
39
    public void testBug59609() throws ParseException {
40
        JMeterContext context = JMeterContextService.getContext();
41
        JSONPostProcessor processor = setupProcessor(context, "0", false);
42
43
        String innerValue = "{\"a\":\"one\",\"b\":\"two\"}";
44
        String data = "{\"context\":" + innerValue + "}";
45
        SampleResult result = new SampleResult();
46
        result.setResponseData(data.getBytes(StandardCharsets.UTF_8));
47
48
        JMeterVariables vars = new JMeterVariables();
49
        context.setVariables(vars);
50
        context.setPreviousResult(result);
51
52
        processor.setJsonPathExpressions("$.context");
53
        processor.process();
54
55
        JSONParser parser = new JSONParser(0);
56
        Object expectedValue = parser.parse(innerValue);
57
        Assert.assertEquals(expectedValue, parser.parse(vars.get(VAR_NAME)));
58
        Assert.assertEquals("1", vars.get(VAR_NAME + "_matchNr"));
59
    }
60
61
    @Test
62
    public void testExtractSimpleArrayElements() {
63
        JMeterContext context = JMeterContextService.getContext();
64
        JSONPostProcessor processor = setupProcessor(context, "-1");
65
        String data = "[1,2,3]";
66
        SampleResult result = new SampleResult();
67
        result.setResponseData(data.getBytes(StandardCharsets.UTF_8));
68
        JMeterVariables vars = new JMeterVariables();
69
        context.setVariables(vars);
70
        context.setPreviousResult(result);
71
72
        processor.setJsonPathExpressions("$[*]");
73
        processor.process();
74
75
        Assert.assertEquals("1,2,3", vars.get(VAR_NAME+ "_ALL"));
76
        for (int i = 1; i <= 3; i++) {
77
            String v = Integer.toString(i);
78
            Assert.assertEquals(v, vars.get(VAR_NAME + "_" + v));
79
        }
80
81
        Assert.assertEquals("3", vars.get(VAR_NAME + "_matchNr"));
82
    }
83
84
    @Test
85
    public void testExtractComplexElements() {
86
        JMeterContext context = JMeterContextService.getContext();
87
        JSONPostProcessor processor = setupProcessor(context, "-1");
88
        String data = "[{\"a\":[1,{\"d\":2},3]},[\"b\"],3]";
89
        SampleResult result = new SampleResult();
90
        result.setResponseData(data.getBytes(StandardCharsets.UTF_8));
91
        JMeterVariables vars = new JMeterVariables();
92
        context.setVariables(vars);
93
        context.setPreviousResult(result);
94
95
        processor.setJsonPathExpressions("$[*]");
96
        processor.process();
97
98
        String jsonWithoutOuterParens = data.substring(1, data.length() - 1);
99
        Assert.assertEquals(jsonWithoutOuterParens, vars.get(VAR_NAME + "_ALL"));
100
101
        Assert.assertEquals("{\"a\":[1,{\"d\":2},3]}", vars.get(VAR_NAME + "_1"));
102
        Assert.assertEquals("[\"b\"]", vars.get(VAR_NAME + "_2"));
103
        Assert.assertEquals("3", vars.get(VAR_NAME + "_3"));
104
105
        Assert.assertEquals("3", vars.get(VAR_NAME + "_matchNr"));
106
    }
107
108
    private JSONPostProcessor setupProcessor(JMeterContext context,
109
    String matchNumbers) {
110
        return setupProcessor(context, matchNumbers, true);
111
    }
112
113
    private JSONPostProcessor setupProcessor(JMeterContext context,
114
            String matchNumbers, boolean computeConcatenation) {
115
        JSONPostProcessor processor = new JSONPostProcessor();
116
        processor.setThreadContext(context);
117
        processor.setRefNames(VAR_NAME);
118
        processor.setMatchNumbers(matchNumbers);
119
        processor.setComputeConcatenation(computeConcatenation);
120
        return processor;
121
    }
122
123
}

Return to bug 59609