0

我在下面使用此代码,它在 Android 2.3.3 中完美运行。但是,在 4.0+ 中,它无法以某种方式连接到数据库。我看到一些关于你需要在异步课程中获得它的帖子。我也试过了,但我似乎无法正常工作。我可能用错了,但我很难理解。

 public class connector extends Activity {
    /** Called when the activity is first created. */

       TextView txt;
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        getServerData(null);
    }
     //i use my real ip here

    public String getServerData(String returnString) {
        System.out.println("going to connector class");
       InputStream is = null;
       final String KEY_121 = "http://10.0.0.128/connector.php";
       String result = "";
        //the year data to send
      //  ArrayList<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>();
      //  nameValuePairs.add(new BasicNameValuePair("year","1970"));

        //http post
        try{
                HttpClient httpclient = new DefaultHttpClient();
                HttpPost httppost = new HttpPost(KEY_121);
               // httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
                HttpResponse response = httpclient.execute(httppost);
                HttpEntity entity = response.getEntity();
                is = entity.getContent();

        }catch(Exception e){
                Log.e("log_tag", "Error in http connection "+e.toString());
        }

        //convert response to string
        try{
                BufferedReader reader = new BufferedReader(new InputStreamReader(is,"iso-8859-1"),8);
                StringBuilder sb = new StringBuilder();
                String line = null;
                while ((line = reader.readLine()) != null) {
                        sb.append(line + "\n");
                }
                is.close();
                result=sb.toString();
        }catch(Exception e){
                Log.e("log_tag", "Error converting result "+e.toString());
        }
        //parse json data
        try{
                JSONArray jArray = new JSONArray(result);
                for(int i=0;i<jArray.length();i++){
                        JSONObject json_data = jArray.getJSONObject(i);
                        Log.i("log_tag","ID: "+json_data.getInt("ID")+
                                ", \nActara: "+json_data.getString("Actara")
                        );
                        //Get an output to the screen
                        returnString += "\n\t" + jArray.getJSONObject(i); 
                }
        }catch(JSONException e){
                Log.e("log_tag", "Error parsing data "+e.toString());
        }
        return returnString; 
    }    

    }

Logcat 错误(在 4.0+ 上):

11-12 12:02:35.658: E/log_tag(14083): Error in http connection android.os.NetworkOnMainThreadException
11-12 12:02:35.658: E/log_tag(14083): Error converting result java.lang.NullPointerException
11-12 12:02:35.663: E/log_tag(14083): Error parsing data org.json.JSONException: End of input at character 0 of 

只有第一个错误行很重要,因为它无法连接到数据库,它给出了一个 nullPointer(第二个和第三个错误)。

这是我在异步中尝试过的:

    public class connector extends Activity {
    /** Called when the activity is first created. */

       TextView txt;
    @Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    new BackgroundAsyncTask().execute();

}

 public class BackgroundAsyncTask extends
    AsyncTask<Void, Integer, Void> {

        InputStream is = null;
        final String KEY_121 = "http://10.0.0.128/connector.php";
        String result = "";
        String returnString = "";

        protected void onPostExecute(Void result) {

        }

        @Override
        protected void onPreExecute() {
        System.out.println("onPreExecute");
        }

        protected Void doInBackground(String... params) {
             try{
                 System.out.println("background in progress");
                 HttpClient httpclient = new DefaultHttpClient();
                 HttpPost httppost = new HttpPost(KEY_121);
                // httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
                 HttpResponse response = httpclient.execute(httppost);
                 HttpEntity entity = response.getEntity();
                 is = entity.getContent();

         }catch(Exception e){
                 Log.e("log_tag", "Error in http connection "+e.toString());
         }

         //convert response to string
         try{
                 BufferedReader reader = new BufferedReader(new InputStreamReader(is,"iso-8859-1"),8);
                 StringBuilder sb = new StringBuilder();
                 String line = null;
                 while ((line = reader.readLine()) != null) {
                         sb.append(line + "\n");
                 }
                 is.close();
                 result=sb.toString();
         }catch(Exception e){
                 Log.e("log_tag", "Error converting result "+e.toString());
         }
         //parse json data
         try{
                 JSONArray jArray = new JSONArray(result);
                 for(int i=0;i<jArray.length();i++){
                         JSONObject json_data = jArray.getJSONObject(i);
                         Log.i("log_tag","ID: "+json_data.getInt("ID")+
                                 ", \nActara: "+json_data.getString("Actara")
                         );
                         //Get an output to the screen
                         returnString += "\n\t" + jArray.getJSONObject(i); 
                 }
         }catch(JSONException e){
                 Log.e("log_tag", "Error parsing data "+e.toString());
         }
        return null;
        }

        protected void onProgressUpdate(Integer... values) {

        }

        @Override
        protected Void doInBackground(Void... params) {
            // TODO Auto-generated method stub
            return null;
        }

    }

}

有人可以帮助我吗?我不确定真正的原因是为什么它不适用于 4.0+。
如果您需要更多信息,请说出来,我会发布。
代码可能有点乱,我还没有真正“清理”它。

4

4 回答 4

2

从 Android 3.0 开始,你不能在主线程上做网络事情。为什么?因为网络问题会导致用户界面变慢。所以你必须在一个新线程中做所有的 http 东西。您走在正确的道路上,但您在 AsyncTask 中犯了一个错误。删除异步任务中的空 doInBackground 方法并在您的方法上写入 @Override。

于 2012-11-12T11:34:21.893 回答
1

好的对...搜索了几个小时后,提出了这个问题,然后10分钟后,您找到了解决方案...

选项 1:
我添加了这一行:

 StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
 StrictMode.setThreadPolicy(policy);

但我建议不要使用选项 1,这实际上是一个糟糕的解决方案。使用选项 2!
//================================================= ============================
选项2:

使用本教程制作正确的ASyncTask:http://www.elvenware.com/charlie/development/android/SimpleHttpGetThread.html

//================================================= ============================
使用 ASyncTask 作为最终任务(选项 2)。

于 2012-11-12T11:26:05.530 回答
1

android.os.NetworkOnMainThreadException

这个错误来自 HoneyComb(3.0 或更高版本)。如文档所述,您无法在其主线程上执行网络操作。要解决这个问题,您必须使用处理程序或异步任务。AFAIK 没有其他方法可以做到这一点。

您可以查看此内容以了解更多详细信息为什么 ICS 会导致您的应用程序崩溃

尝试使用下面的代码片段

new Thread(){
    public void run(){
        //do your Code Here    
    }
}.start();
于 2012-11-12T11:42:58.457 回答
0

为什么你要传递null网络连接和网络服务的功能。?

getServerData(null);
于 2012-11-12T11:14:46.307 回答