2015-12-02 100 views
0

我正在運行一個程序,該程序使用POST請求向PHP頁面報告有關泵運行時間和放大器到服務器的數據。該系統在幾個Arduino Pro Minis上運行良好。我正在使用328和Arduino Uno引導程序構建的電路板上進行測試,以及4個不同的POST請求,兩個工作和兩個失敗。如何解決400錯誤請求

我相信這是由Arduino糟糕地形成POST請求引起的,但是我無法驗證這一點,因爲Arduino Serial.prints是正確的字符串。如果我手動硬編碼字符串,它也可以。

我形成數據是這樣的:

byte runtime = analogRead(A3); // generates random data 
float amps = analogRead(A2)/100; 
char cruntime[4]; // create char array for runtime 
char camps[5]; 
dtostrf(runtime, 4, 0, cruntime); 
dtostrf(amps, 2, 1, camps); 
String sruntime = String(cruntime); 
sruntime.trim(); 
String samps = String(camps); 
samps.trim(); 
String cwpdata = "serial=test&runtime=" + sruntime + "&amps=" + samps; // posted to server 

我已經檢查我的錯誤的服務器,但無法找到的這些記錄。無論如何,我可以看到每次發佈的內容,所以我可以看到請求未正確形成的位置?

這裏是Arduino的代碼發佈數據:

void postData(String inputData, String filename) { 
    if (client.connect(server, 80)) { 
    Serial.println("connected"); 
    // Make a HTTP request: 
    client.println("POST /dev/telemetry/test/" + filename + ".php HTTP/1.1"); 
    client.println("Host: www.SERVER.com"); // changed for privacy 
    client.println("Content-Type: application/x-www-form-urlencoded"); 
    client.print("Content-Length: "); 
    client.println(inputData.length()); 
    Serial.println(inputData); 
    Serial.print("Data Length: "); 
    Serial.println(inputData.length()); 
    client.println("Connection: close"); 
    client.println(); 
    client.println(inputData); 
    client.println(); 
    } // close if client 

    wdt_reset(); 
    unsigned long startMillis = millis(); 
    unsigned long endMillis = startMillis + timeout; 
    while(client.connected() && (millis() < endMillis)) { 
    wdt_reset(); 
    while(client.available()) { 
     char ch = client.read(); 
     Serial.print(ch); 
     wdt_reset(); 
    } 
    } 
    // if the server's disconnected, stop the client: 
    Serial.println(); 
    client.stop(); 
    int memory = freeMemory(); 
    if (memory < 125) { 
    delay(15000); 
    } 
} 
+1

服務器上應該有一個error.log文件。 –

+0

我查看了所有發現的錯誤日誌,但沒有看到它。我會再看看。 – pekasus

+0

我再次查看了該文件夾中的所有錯誤日誌以及上面的文件夾,結果什麼都沒發現。我查看了原始服務器日誌,並沒有顯示400。 – pekasus

回答

1

我會大膽地猜測,有時,你inputData包含他們在POST體發送之前不正確編碼的轉義字符。

"serial=test&runtime=" + sruntime + "&amps=" + samps以內,如果sruntimesamps包含非轉義字符,它可能很好地拋出服務器端解析。有沒有隱藏在Serial.println(inputData)中的可能被忽略的「不可打印」控制字節?

順便說一句,「安全」字符是A-Z,a-z,0-9,短劃線,下劃線,點,波浪線和加號(意思是空格)。在發送之前,其他一切必須是percent-encoded。如果數據碰巧是Unicode,它會得到一個little hairier

+0

我想你可能是對的。有一次,我在inputData中找到了一個空格,這就是爲什麼我添加了trim()命令,但這並不總是有效的。這讓我很討厭C語言,因爲它將數據轉換爲字符串非常複雜,並且各種各樣的東西都在引擎蓋下發生。 – pekasus