如何通过SOAP与Java实现FritzBox重连?程序无报错未生效求助
FritzBox SOAP重连失败排查与修复
你的代码和SOAP请求存在几个关键问题,导致路由器未执行重连操作,具体分析和修复方案如下:
核心问题点
1. HTTP请求头格式错误
第一行POST请求结尾缺少\r\n,HTTP协议要求每个头字段必须以\r\n结尾,这会导致服务器无法正确解析请求结构,直接忽略或拒绝处理请求。
2. Content-Length计算错误
你用soapXML.toString().length()获取字符数作为Content-Length,但HTTP协议要求该值为字节数。UTF-8编码下部分字符会占用多个字节,直接用字符数会导致长度不匹配,服务器可能丢弃或拒绝处理报文。
3. 缺少认证头
FritzBox默认开启HTTP基础认证,你的请求未携带Authorization头,服务器会直接拒绝执行敏感操作(比如重连),这是最常见的失败原因。
4. 未读取服务器响应
代码仅发送请求,未获取服务器返回的状态码或错误信息,无法定位请求失败的具体原因(比如401未授权、404路径错误等)。
修复后的完整代码
import java.io.*; import java.net.Socket; import java.nio.charset.StandardCharsets; import java.util.Base64; public void reconnect() { StringBuilder soapXML = new StringBuilder(); soapXML.append("<?xml version=\"1.0\" encoding=\"utf-8\"?>"); soapXML.append("<s:Envelope s:encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\" xmlns:s=\"http://schemas.xmlsoap.org/soap/envelope/\">"); soapXML.append(" <s:Body>"); soapXML.append(" <u:ForceTermination xmlns:u=\"urn:dslforum-org:service:WANIPConnection:1\" />"); soapXML.append(" </s:Body>"); soapXML.append("</s:Envelope>"); Socket socket = null; BufferedWriter bw = null; BufferedReader br = null; try { socket = new Socket("192.168.178.1", 49000); bw = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), StandardCharsets.UTF_8)); br = new BufferedReader(new InputStreamReader(socket.getInputStream(), StandardCharsets.UTF_8)); // 计算SOAP报文的字节长度,符合HTTP协议要求 byte[] soapBytes = soapXML.toString().getBytes(StandardCharsets.UTF_8); int contentLength = soapBytes.length; // 替换为你的FritzBox用户名和密码(无用户名则留空字符串) String username = "你的路由器用户名"; String password = "你的路由器密码"; String auth = Base64.getEncoder().encodeToString((username + ":" + password).getBytes(StandardCharsets.UTF_8)); // 修正HTTP头格式,添加认证信息 bw.write("POST /upnp/control/wanipconnection1 HTTP/1.1\r\n"); bw.write("HOST: 192.168.178.1:49000\r\n"); bw.write("CONTENT-LENGTH: " + contentLength + "\r\n"); bw.write("CONTENT-TYPE: text/xml; charset=\"utf-8\"\r\n"); bw.write("SOAPACTION: \"urn:dslforum-org:service:WANIPConnection:1#ForceTermination\"\r\n"); bw.write("USER-AGENT: AVM UPnP/1.0 Client 1.0\r\n"); bw.write("Authorization: Basic " + auth + "\r\n"); bw.write("\r\n"); // 直接发送字节流,避免字符编码转换问题 socket.getOutputStream().write(soapBytes); socket.getOutputStream().flush(); // 读取服务器响应,用于排查问题 String line; System.out.println("服务器响应内容:"); while ((line = br.readLine()) != null) { System.out.println(line); } } catch (IOException e) { e.printStackTrace(); } finally { try { if(br != null) br.close(); } catch (IOException e) {} try { if(bw != null) bw.close(); } catch (IOException e) {} try { if(socket != null) socket.close(); } catch (IOException e) {} } }
额外验证步骤
- 确认FritzBox的UPnP功能已开启(路径:路由器后台→网络→UPnP设置)。
- 检查
/upnp/control/wanipconnection1路径是否正确:访问http://192.168.178.1:49000/tr64desc.xml,找到WANIPConnection服务的controlURL字段确认。
内容的提问来源于stack exchange,提问作者TryToProgram
相关产品推荐
相关产品推荐

