首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> J2ME

J2ME 呼叫 .NET Web Service 完整實戰:中文編碼難題徹底解決

     編輯:J2ME

專案背景與挑戰

  • 客戶端:J2ME (MIDP 2.0, CLDC 1.1)
  • 伺服端:ASP.NET Web Service (.asmx),預設 UTF-8 編碼
  • 核心衝突:Java 預設 ISO-8859-1,.NET 預設 UTF-8,中文參數傳遞與回傳雙向亂碼
  • 目標:雙邊正確編解碼,最小化客戶端代碼複雜度

開發環境

  • JDK 1.6, NetBeans 4.1, Mobility Pack 4.1, WTK 2.3
  • 安裝順序:JDK → WTK → NetBeans → Mobility Pack

.NET Web Service 端配置(關鍵三步)

1. 服務代碼


[WebMethod]
public string Hello(string str) {
    return "你好:" + str;
}

2. web.config 全域化編碼設定



    

強制 ASP.NET 以 GB2312 解碼請求、編碼回應。

3. 開啟 HTTP GET/POST 協議(預設關閉)



    
        
        
    

原因:J2ME HttpConnection 簡易呼叫多用 GET,若伺服端僅支援 SOAP/POST,則需完整 SOAP 封裝,大幅增加客戶端代碼量。

J2ME 客戶端實現

核心代碼


package com.sun.j2me;

import javax.microedition.midlet.*;
import javax.microedition.lcdui.*;
import javax.microedition.io.*;
import java.io.*;

public class HttpTest extends MIDlet {
    private Display display;

    public HttpTest() {
        display = Display.getDisplay(this);
    }

    protected void startApp() {
        HttpConnection hc = null;
        DataInputStream dis = null;
        try {
            // 1. 構建 URL,中文參數直接拼接(依賴伺服端 GB2312 解碼)
            String url = "https://localhost/WebService1/Service1.asmx/Hello?str=呱呱";
            
            // 2. 開啟連線
            hc = (HttpConnection) Connector.open(url);
            
            // 3. 關鍵:設定請求標頭 charset=gb2312
            hc.setRequestProperty("Content-Type", "text/html;charset=gb2312");
            
            // 4. 讀取回應
            int len = (int) hc.getLength();
            dis = new DataInputStream(hc.openInputStream());
            
            if (len > 0) {
                byte[] data = new byte[len];
                dis.readFully(data);
                // 5. 關鍵:回應以 UTF-8 解碼(.NET XML 回應預設 UTF-8)
                String content = new String(data, "UTF-8");
                
                Form form = new Form("HTTP Test");
                form.append(content);  // 顯示含 XML 標籤的原始回應
                display.setCurrent(form);
            }
        } catch (Exception e) {
            System.out.println(e);
            notifyDestroyed();
        } finally {
            try { if (dis != null) dis.close(); } catch (Exception ignored) {}
            try { if (hc != null) hc.close(); } catch (Exception ignored) {}
        }
    }

    protected void pauseApp() {}
    protected void destroyApp(boolean unconditional) {}
}

編碼流向圖解

階段資料形態編碼關鍵代碼/設定
客戶端構建 URL字串 "呱呱"Java 內部 Unicode無特殊處理
HTTP 請求發送位元組流GB2312 (由伺服端要求)setRequestProperty("Content-Type", "text/html;charset=gb2312")
伺服端接收字串參數GB2312 → UnicoderequestEncoding="gb2312"
業務邏輯處理字串 "你好:呱呱"Unicode正常字串操作
XML 序列化回應XML 文檔UTF-8 (ASP.NET 預設)responseEncoding="gb2312" 僅影響非 XML 回應
客戶端讀取位元組陣列原始 UTF-8 位元組new String(data, "UTF-8")
顯示字串Unicode → 螢幕字型MIDP 實現自動處理

進階:解析 XML 回應獲取純文字

.NET Web Service 回應為 SOAP XML 格式:



你好:呱呱

J2ME 可用 kXML、NanoXML、或簡易字串截取解析 <string> 節點內容。

最佳實踐總結

  1. 統一編碼協議:雙方約定「傳輸層 GB2312,應用層 Unicode」,或雙邊 UTF-8(需 J2ME 確支援)
  2. 傳輸位元組流:避免字串編碼轉換,客戶端 OutputStream.write(bytes),伺服端 Request.BinaryRead
  3. Java-Java 通訊:DataOutputStream.writeUTF() / DataInputStream.readUTF()(修改版 UTF-8),零配置零亂碼
  4. 錯誤處理:捕獲 IOException、CertificateException (HTTPS)、逾時,給用戶友好提示
  5. 安全性:生產環境必須 HTTPS,驗證伺服端憑證,參數簽名防篡改

常見坑點對照表

現象原因修正
中文參數變亂碼未設定 Content-Type charset加上 charset=gb2312
回應中文變問號用 ISO-8859-1 解碼 UTF-8 位元組new String(data, "UTF-8")
HTTP 405 Method Not Allowed.NET 未開啟 HttpGet/HttpPostweb.config 加入 protocols 區段
模擬器能連,真機不能真機無公網 IP/防火牆/APN 限制確認 APN 設定、伺服端公網可達、使用 HTTPS

結語

J2ME 呼叫 .NET Web Service 的核心難點在於編碼協議不一致。通過 web.config 統一伺服端編碼、HttpConnection.setRequestProperty 宣告客戶端編碼、new String(bytes, "UTF-8") 正確解碼回應,三步驟徹底解決中文亂碼。此模式同樣適用於 J2ME 對接 Java/PHP/Python 等任意後端服務——明確協議、顯式聲明、嚴格驗證,是跨平台整合的黃金法則。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved