-1

I was trying to start a XML parse from URL with my previous post: Parsing XML on Android

Therefore, I tried to get the XML file using InputStream and parse the text from it using DocumentBuilder.

I was trying to use SharedPreferences to store my XML file offline.

<?xml version='1.0' encoding='utf-8' standalone='yes' ?>
<map>
<string>
    <name>username</name>
    <value>mium</value>
</string>

This is my XML file.

  private boolean parseXML(String target){
    cache_string = getSharedPreferences("cache_userfiles", Context.MODE_PRIVATE);
    cache_string_editor = cache_string.edit();
    cache_string_editor.apply();
    try {
        URL url = new URL(target);
        InputStream inputStream = url.openStream();
        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
        DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
        Document document = documentBuilder.parse(inputStream);
        Element element = document.getDocumentElement();
        element.normalize();
        NodeList nodeList = document.getElementsByTagName("string");
        for (int current=0; current < nodeList.getLength(); current++){
            Node node = nodeList.item(current);
            if (node.getNodeType() == Node.ELEMENT_NODE){
                Element element_specific = (Element) node;
                cache_string_editor.putString(getValue("name", element_specific), getValue("value", element_specific));
                cache_string_editor.apply();
            }
        }
        return true;
    } catch (Exception e){
        e.printStackTrace();
        return false;
    }
}

And this is my parse code.

To use this code, in my main thread, I used:

if (parseXML("http://www.myserver.com/file.xml")){
    Log.d(TAG, "Success");
}

However, I keep getting android.os.NetworkOnMainThreadException. I tried adding thread and handler, but it keeps getting me an error. What's the problem? I know it's unable to handle network process on main thread, but I don't know exactly how to solve the problem.

R7G
  • 1,000
  • 1
  • 10
  • 15
Mium
  • 303
  • 1
  • 2
  • 12

2 Answers2

1

You can't use Network on main thread since it will block UI components. you need to use AsyncTask for this .

new AsyncTask<Void ,Void ,Boolean>(){
            @Override
            protected Boolean doInBackground(Void... voids) {
                return parseXML("http://www.myserver.com/file.xml");
            }

            @Override
            protected void onPostExecute(Boolean aBoolean) {
                super.onPostExecute(aBoolean);
                Log.d(TAG, "Success "+aBoolean);
            }
        }.execute();
R7G
  • 1,000
  • 1
  • 10
  • 15
  • Now I get an error: Can't create handler inside thread that has not called Looper.prepare(),, it's really tough.. – Mium Aug 18 '18 at 19:44
  • this must be because of the Shared Preference you are using directly in the asynctask please refer this answer [link of answer](https://stackoverflow.com/questions/23596903/how-do-i-get-sharedpreferences-in-asynctask) and create a local shared preference object in the asynctask . – R7G Aug 19 '18 at 03:20
1

The NetworkOnMainThreadException occurs when you perform a network operation on your main (GUI) thread - and that is not allowed as a long running operation would make the app unresponsive.

To solve the problem, wrap your operation in an AsyncTask. This will offload the operation onto a separate thread of execution. When the task is done, you call its onPostExecute member to pass data back to your main thread.

Alexander van Oostenrijk
  • 4,644
  • 3
  • 23
  • 37