1

URLFetch クラスを使用して、Google App エンジンで HTTP Post を PHP ファイル (別の Web サイト) に送信しました。

これは私が持っているものです

try{
byte[] data = ("EMAIL=bo0@gmail.com&TITLE=evolution&COMMENT=comments&PRICE=5000").getBytes("UTF-8");
URL url = new URL("http://www.box.com/nost.php");
HTTPRequest request = new HTTPRequest(url, HTTPMethod.POST);
request.setPayload(data);
HTTPResponse response = URLFetchServiceFactory.getURLFetchService().fetch(request);
}

ローカルに展開すると、これは完全にうまくいくようです。ただし、Google App Engine で公開すると、半分の時間しか機能しません。(つまり、まったく同じデータを使用しても、投稿を複数回押すと、エラーまたは成功のいずれかになります)

私はデータを変更していないので、これは完全にランダムに見えます。なぜこれが起こっているのか、誰かアドバイスをもらえますか?

編集: これは動作するコードです。私の php は、gae が作成している http 要求をブロックしていたようです。キャッチブロック内で再帰を使用して、成功するまで試行を続けることで修正しました。

try {
    URL url = new URL("http://www.mywebsite.com/myfile.php");
    HttpURLConnection connection = (HttpURLConnection) url.openConnection();
    connection.setDoOutput(true);
    connection.setRequestMethod("POST");

    OutputStreamWriter writer = new OutputStreamWriter(connection.getOutputStream());
writer.write("EMAIL="+URLEncoder.encode("sam@gmail.com", "UTF-8")+
"&TITLE="+URLEncoder.encode("myTitle", "UTF-8")+
"&PRICE="+URLEncoder.encode(String.valueOf(10000), "UTF-8"));
writer.close();

if (connection.getResponseCode() == HttpURLConnection.HTTP_OK) {
// OK
return true;
} else {
// Server returned HTTP error code.
//keep retrying until you succeed!! fighting!!
return newPost(postComponent);
}
} catch (MalformedURLException e) {
e.printStackTrace();
return false;
} catch (IOException e) {
e.printStackTrace();
return false;
}
catch (Exception e){
e.printStackTrace();
//ah dam probably server is down so you went stack overflow I give up
return false;
}
4

1 に答える 1

3

URLFetch サービスを使用する代わりに、java.net を使用することを強くお勧めします。

私の経験では、これが進むべき道です。コレクションをループして多数の POST リクエストをリモート サーバーに送信し、カウントと出力をブラウザに書き込む前にテスト ケースをセットアップして、成功した数と失敗した数を確認できるようにしました。

結果は興味深いものでした。ログに例外が記録されているのを見て、「ああ、ネットワークがダメな理由を突き止めようとして時間が無駄になった!」と思いました。さて、私は 10 万のテスト ケースの結果を調べましたが、すべて成功していました。

例外を掘り下げた後、たとえば、サーバーから 500 応答を受け取った場合、コードが実際に 2 回目の要求を試みていることが明らかになりました。これが、約 500 件のエラーにもかかわらず、すべてのケースが成功した理由です。

これはまさに私が探していたものでした。サーバーの問題や小さなネットワークの問題に対して独自のエラー ハンドラーを作成する必要がなく、ライブラリがそれを処理してくれました。

java.net - HTTPURLConnectionは、データをサーバーに送信する際に非常に信頼できることが証明されています。

次の例では、何らかのフォーム データを含む URL に対して HTTP POST 要求を作成します。

import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLEncoder;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.IOException;
import java.io.OutputStreamWriter;

// ...
        String message = URLEncoder.encode("my message", "UTF-8");

        try {

            // this is your url that you're posting to
            URL url = new URL("http://www.box.com/nost.php");

            // create and open the connection using POST 
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setDoOutput(true);
            connection.setRequestMethod("POST");

            OutputStreamWriter writer = new OutputStreamWriter(connection.getOutputStream());

            // this is your data that you're sending to the server! 
            writer.write("EMAIL=bo0@gmail.com&TITLE=evolution&COMMENT=comments&PRICE=5000");

            writer.close();

            // this is where you can check for success/fail. 
             // Even if this doesn't properly try again, you could make another 
              // request in the ELSE for extra error handling! :)        
            if (connection.getResponseCode() == HttpURLConnection.HTTP_OK) {
                // OK
            } else {
                // Server returned HTTP error code.
            }
        } catch (MalformedURLException e) {
            // ...
        } catch (IOException e) {
            // ...
        }

php ファイルに対してリクエストを行っているのではなく、サーバーに対してリクエストを行っていることを思い出してください。内部ではすべて HTTP であるため、ファイルの種類に違いはありません。お役に立てれば!

リモート エンドポイントとクエリ文字列データを使用するように、Google の例を編集しました。

于 2012-11-06T06:35:08.583 に答える