【问题标题】:java.lang.IllegalArgumentException in URL's path in JavaJava 中 URL 路径中的 java.lang.IllegalArgumentException
【发布时间】:2021-02-20 15:38:25
【问题描述】:

我有一个向接口发送 Web 服务请求的 java 代码。现在对于其中一个界面,我收到以下错误

java.lang.IllegalArgumentException: Illegal character(s) in message header field: http://10.11.22.33:8088/platform-core/smsGateMgw
    at sun.net.www.protocol.http.HttpURLConnection.checkMessageHeader(HttpURLConnection.java:522)
    at sun.net.www.protocol.http.HttpURLConnection.isExternalMessageHeaderAllowed(HttpURLConnection.java:492)
    at sun.net.www.protocol.http.HttpURLConnection.setRequestProperty(HttpURLConnection.java:3057)
    at com.in.ci.fioutbound.custom.SmsSender.sendSms(SmsSender1.java:255)
    at com.in.ci.fioutbound.custom.SmsSender.executeOutboundRequest(SmsSender1.java:104)

我猜这是因为 URL 中的“-”,但不确定。 有人可以让我知道如何对 URL 的路径进行编码,或者是否有其他方法来处理这个问题。 这就是我的 java 代码现在的样子

URL smsServiceUrl = new URL(smsService);
URLConnection conn = smsServiceUrl.openConnection();
HttpURLConnection httpconn = (HttpURLConnection)conn;
ByteArrayOutputStream bout = new ByteArrayOutputStream();

byte[] buffer = new byte[reqXml.length()];
buffer = reqXml.getBytes();
bout.write(buffer);
byte[] b = bout.toByteArray();

httpconn.setRequestProperty("Content-Length", String.valueOf(b.length));
httpconn.setRequestProperty("Content-Type", "text/xml;charset=utf-8");
httpconn.setRequestProperty(smsService, smsService);
httpconn.setRequestMethod("POST");

httpconn.setDoOutput(true);
httpconn.setDoOutput(true);

OutputStream out = httpconn.getOutputStream();
out.write(b);
InputStreamReader isr = new InputStreamReader(httpconn.getInputStream());
  
BufferedReader in = new BufferedReader(isr);
while ((responseString = in.readLine()) != null) {
    outputString = outputString + responseString;
}

此外,相同的代码在具有相同 URL 的另一台服务器上也能正常工作。唯一的区别是两个服务器之间的 java 1.7 和 1.8。那么这是 java 1.8 中的新功能吗?

【问题讨论】:

    标签: java url httpconnection


    【解决方案1】:

    HTTP 1.1 在RFC 2616 中定义。 headers在4.2节中定义,引用RFC 822,定义它们的是3.2节,它本身将header字段名称定义为

    field-name  =  1*<any CHAR, excluding CTLs, SPACE, and ":">
    

    这意味着您不能在标题名称中使用冒号 (:)。

    当您执行 httpconn.setRequestProperty(smsService, smsService); 时,您正在设置一个包含 :http://... 中的那个)的字段名称,这对于值来说是合适的,但对于名称来说却不是。

    该标题似乎没有任何意义,因此您应该能够安全地从代码中删除该整行。

    编辑:

    我刚刚注意到你没有使用我认为你正在使用的类。您使用的是sun.net.www.protocol.http.HttpURLConnection 而不是java.net.HttpURLConnection

    这可以解释为什么它在 Java 7 中有效,因为如果您查看该类中 checkMessageHeader 方法的 source code,它不会检查它是否包含 :

    private void checkMessageHeader(String key, String value) {
            char LF = '\n';
            int index = key.indexOf(LF);
            if (index != -1) {
                throw new IllegalArgumentException(
                    "Illegal character(s) in message header field: " + key);
            }
    
            else {
                if (value == null) {
                    return;
                }
    
                index = value.indexOf(LF);
                while (index != -1) {
                    index++;
                    if (index < value.length()) {
                        char c = value.charAt(index);
                        if ((c==' ') || (c=='\t')) {
                            // ok, check the next occurrence
                            index = value.indexOf(LF, index);
                            continue;
    
                        }
                    }
    
                    throw new IllegalArgumentException(
                        "Illegal character(s) in message header value: " + value);
    
                }
            }
        }
    

    虽然,例如 current version of openjdk 确实如此。

    private void checkMessageHeader(String key, String value) {
        char LF = '\n';
        int index = key.indexOf(LF);
        int index1 = key.indexOf(':');
        if (index != -1 || index1 != -1) {
            throw new IllegalArgumentException(
                "Illegal character(s) in message header field: " + key);
        }
        // ... rest of the method ...
    

    我不确定您在哪个版本的 java 8 上运行它,因为在 OpenJDK 8 的 available source code 中,行号与您的异常不对应,而 OpenJDK 8 似乎没有检查任何一个。

    【讨论】:

    • 那我该怎么处理呢?
    • 你用那个标题做什么?首先,这似乎没有多大意义。
    • 这是一些非常古老的代码,但是我对java的了解有限,我认为它是设置URL值来发送Web服务请求。我可以评论 httpconn.setRequestProperty(smsService, smsService);如果没有意义?
    • 除非 API 明确要求它(我怀疑),否则您必须删除该行,是的。
    • 删除该行后工作正常,非常感谢。我现在只是好奇相同的代码如何在 jdk 1.7 上的另一台服务器上工作
    猜你喜欢
    • 1970-01-01
    • 2019-05-10
    • 1970-01-01
    • 2013-05-31
    • 2021-06-04
    • 1970-01-01
    • 1970-01-01
    • 2014-03-16
    相关资源
    最近更新 更多