• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

hazendaz / httpunit / 636

05 Dec 2025 03:27AM UTC coverage: 80.509%. Remained the same
636

push

github

hazendaz
Cleanup more old since tags

you guessed it, at this point going to jautodoc the rest so the warnings on builds go away ;)

3213 of 4105 branches covered (78.27%)

Branch coverage included in aggregate %.

8249 of 10132 relevant lines covered (81.42%)

0.81 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

63.46
/src/main/java/com/meterware/httpunit/HttpWebResponse.java
1
/*
2
 * MIT License
3
 *
4
 * Copyright 2011-2025 Russell Gold
5
 *
6
 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated
7
 * documentation files (the "Software"), to deal in the Software without restriction, including without limitation
8
 * the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and
9
 * to permit persons to whom the Software is furnished to do so, subject to the following conditions:
10
 *
11
 * The above copyright notice and this permission notice shall be included in all copies or substantial portions
12
 * of the Software.
13
 *
14
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO
15
 * THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
17
 * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
18
 * DEALINGS IN THE SOFTWARE.
19
 */
20
package com.meterware.httpunit;
21

22
import java.io.BufferedInputStream;
23
import java.io.ByteArrayInputStream;
24
import java.io.IOException;
25
import java.io.InputStream;
26
import java.net.HttpURLConnection;
27
import java.net.URL;
28
import java.net.URLConnection;
29
import java.net.UnknownHostException;
30
import java.nio.charset.Charset;
31
import java.util.Enumeration;
32
import java.util.Hashtable;
33
import java.util.StringTokenizer;
34
import java.util.Vector;
35

36
/**
37
 * A response from a web server to an Http request.
38
 **/
39
class HttpWebResponse extends WebResponse {
40

41
    private String _referer;
42

43
    /**
44
     * Constructs a response object from an input stream.
45
     *
46
     * @param frame
47
     *            the target window or frame to which the request should be directed
48
     * @param url
49
     *            the url from which the response was received
50
     * @param connection
51
     *            the URL connection from which the response can be read
52
     **/
53
    HttpWebResponse(WebConversation client, FrameSelector frame, URL url, URLConnection connection,
54
            boolean throwExceptionOnError) throws IOException {
55
        super(client, frame, url);
1✔
56
        if (HttpUnitOptions.isLoggingHttpHeaders()) {
1!
57
            System.out.println("\nReceived from " + url);
×
58
        }
59
        readHeaders(connection);
1✔
60

61
        /** make sure that any IO exception for HTML received page happens here, not later. **/
62
        if (_responseCode < HttpURLConnection.HTTP_BAD_REQUEST || !throwExceptionOnError) {
1✔
63
            InputStream inputStream = getInputStream(connection);
1✔
64
            defineRawInputStream(new BufferedInputStream(inputStream));
1✔
65
            String contentType = getContentType();
1✔
66
            if (contentType.startsWith("text")) {
1✔
67
                loadResponseText();
1✔
68
            }
69
        }
70
    }
1✔
71

72
    HttpWebResponse(WebConversation client, FrameSelector frame, WebRequest request, URLConnection connection,
73
            boolean throwExceptionOnError) throws IOException {
74
        this(client, frame, request.getURL(), connection, throwExceptionOnError);
1✔
75
        super.setWithParse(!request.getMethod().equals("HEAD"));
1✔
76
        _referer = request.getReferer();
1✔
77
    }
1✔
78

79
    /**
80
     * get the input stream for the given connection
81
     *
82
     * @param connection
83
     *
84
     * @return
85
     *
86
     * @throws IOException
87
     */
88
    private InputStream getInputStream(URLConnection connection) throws IOException {
89
        InputStream result = null;
1✔
90
        // check whether there is an error stream
91
        if (isResponseOnErrorStream(connection)) {
1✔
92
            result = ((HttpURLConnection) connection).getErrorStream();
1✔
93
        } else {
94
            // if there is no error stream it depends on the response code
95
            try {
96
                result = connection.getInputStream();
1✔
97
            } catch (java.io.FileNotFoundException fnfe) {
1✔
98
                // as of JDK 1.5 a null inputstream might have been returned here
99
                // see bug report [ 1283878 ] FileNotFoundException using Sun JDK 1.5 on empty error pages
100
                // by Roger Lindsj?
101
                if (!isErrorResponse(connection)) {
1✔
102
                    throw fnfe;
1✔
103
                }
104
                // fake an empty error stream
105
                result = new ByteArrayInputStream(new byte[0]);
1✔
106
            }
1✔
107
        }
108
        return result;
1✔
109
    }
110

111
    /**
112
     * check whether a response code >=400 was received
113
     *
114
     * @param connection
115
     *
116
     * @return
117
     */
118
    private boolean isErrorResponse(URLConnection connection) {
119
        return _responseCode >= HttpURLConnection.HTTP_BAD_REQUEST;
1✔
120
    }
121

122
    /**
123
     * check whether the response is on the error stream
124
     *
125
     * @param connection
126
     *
127
     * @return
128
     */
129
    private boolean isResponseOnErrorStream(URLConnection connection) {
130
        return isErrorResponse(connection) && ((HttpURLConnection) connection).getErrorStream() != null;
1✔
131
    }
132

133
    /**
134
     * Returns the response code associated with this response.
135
     **/
136
    @Override
137
    public int getResponseCode() {
138
        return _responseCode;
1✔
139
    }
140

141
    /**
142
     * Returns the response message associated with this response.
143
     **/
144
    @Override
145
    public String getResponseMessage() {
146
        return _responseMessage;
1✔
147
    }
148

149
    @Override
150
    public String[] getHeaderFieldNames() {
151
        Vector names = new Vector<>();
×
152
        for (Enumeration e = _headers.keys(); e.hasMoreElements();) {
×
153
            names.addElement(e.nextElement());
×
154
        }
155
        String[] result = new String[names.size()];
×
156
        names.copyInto(result);
×
157
        return result;
×
158
    }
159

160
    /**
161
     * Returns the value for the specified header field. If no such field is defined, will return null.
162
     **/
163
    @Override
164
    public String getHeaderField(String fieldName) {
165
        String[] fields = (String[]) _headers.get(fieldName.toUpperCase());
1✔
166
        return fields == null ? null : fields[0];
1✔
167
    }
168

169
    @Override
170
    public String[] getHeaderFields(String fieldName) {
171
        String[] fields = (String[]) _headers.get(fieldName.toUpperCase());
1✔
172
        return fields == null ? new String[0] : fields;
1✔
173
    }
174

175
    @Override
176
    public String toString() {
177
        StringBuilder sb = new StringBuilder("HttpWebResponse [url=");
×
178
        sb.append(getURL()).append("; headers=");
×
179
        for (Enumeration e = _headers.keys(); e.hasMoreElements();) {
×
180
            Object key = e.nextElement();
×
181
            String[] values = (String[]) _headers.get(key);
×
182
            for (String value : values) {
×
183
                sb.append("\n   ").append(key).append(": ").append(value);
×
184
            }
185
        }
×
186
        sb.append(" ]");
×
187
        return sb.toString();
×
188
    }
189

190
    @Override
191
    String getReferer() {
192
        return _referer;
1✔
193
    }
194

195
    // ------------------------------------- private members -------------------------------------
196

197
    private static final String FILE_ENCODING = Charset.defaultCharset().displayName();
1✔
198

199
    private int _responseCode = HttpURLConnection.HTTP_OK;
1✔
200
    private String _responseMessage = "OK";
1✔
201

202
    /**
203
     * set the responseCode to the given code and message
204
     *
205
     * @param code
206
     * @param message
207
     */
208
    private void setResponseCode(int code, String message) {
209
        _responseCode = code;
1✔
210
        _responseMessage = message;
1✔
211
    }
1✔
212

213
    private Hashtable _headers = new Hashtable<>();
1✔
214

215
    /**
216
     * read the response Header for the given connection and set the response code and message accordingly
217
     *
218
     * @param connection
219
     *
220
     * @throws IOException
221
     */
222
    private void readResponseHeader(HttpURLConnection connection) throws IOException {
223
        if (!needStatusWorkaround()) {
1!
224
            setResponseCode(connection.getResponseCode(), connection.getResponseMessage());
1✔
225
        } else {
226
            if (connection.getHeaderField(0) == null) {
×
227
                throw new UnknownHostException(connection.getURL().toExternalForm());
×
228
            }
229

230
            StringTokenizer st = new StringTokenizer(connection.getHeaderField(0));
×
231
            st.nextToken();
×
232
            if (!st.hasMoreTokens()) {
×
233
                setResponseCode(HttpURLConnection.HTTP_OK, "OK");
×
234
            } else {
235
                try {
236
                    setResponseCode(Integer.parseInt(st.nextToken()), getRemainingTokens(st));
×
237
                } catch (NumberFormatException e) {
×
238
                    setResponseCode(HttpURLConnection.HTTP_INTERNAL_ERROR, "Cannot parse response header");
×
239
                }
×
240
            }
241
        }
242
    }
1✔
243

244
    private boolean needStatusWorkaround() {
245
        final String jdkVersion = System.getProperty("java.version");
1✔
246
        return jdkVersion.startsWith("1.2") || jdkVersion.startsWith("1.3");
1!
247
    }
248

249
    private String getRemainingTokens(StringTokenizer st) {
250
        StringBuilder messageBuffer = new StringBuilder(st.hasMoreTokens() ? st.nextToken() : "");
×
251
        while (st.hasMoreTokens()) {
×
252
            messageBuffer.append(' ').append(st.nextToken());
×
253
        }
254
        return messageBuffer.toString();
×
255
    }
256

257
    private void readHeaders(URLConnection connection) throws IOException {
258
        loadHeaders(connection);
1✔
259
        if (connection instanceof HttpURLConnection) {
1✔
260
            readResponseHeader((HttpURLConnection) connection);
1✔
261
        } else {
262
            setResponseCode(HttpURLConnection.HTTP_OK, "OK");
1✔
263
            if (connection.getContentType().startsWith("text")) {
1!
264
                setContentTypeHeader(connection.getContentType() + "; charset=" + FILE_ENCODING);
1✔
265
            }
266
        }
267
    }
1✔
268

269
    private void loadHeaders(URLConnection connection) {
270
        if (HttpUnitOptions.isLoggingHttpHeaders()) {
1!
271
            System.out.println("Header:: " + connection.getHeaderField(0));
×
272
        }
273
        for (int i = 1; true; i++) {
1✔
274
            String headerFieldKey = connection.getHeaderFieldKey(i);
1✔
275
            String headerField = connection.getHeaderField(i);
1✔
276
            if (headerFieldKey == null || headerField == null) {
1!
277
                break;
×
278
            }
279
            if (HttpUnitOptions.isLoggingHttpHeaders()) {
1!
280
                System.out.println("Header:: " + headerFieldKey + ": " + headerField);
×
281
            }
282
            addHeader(headerFieldKey.toUpperCase(), headerField);
1✔
283
        }
284

285
        if (connection.getContentType() != null) {
1!
286
            setContentTypeHeader(connection.getContentType());
1✔
287
        }
288
    }
1✔
289

290
    private void addHeader(String key, String field) {
291
        _headers.put(key, HttpUnitUtils.withNewValue((String[]) _headers.get(key), field));
1✔
292
    }
1✔
293

294
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc