0

I'm trying to populate a database from an xml file. It work pretty well, but the problem is when I try to load the xml from a server. I've spent hours and hours, trying lots of different implementations but I always receive an exception. Here is my current code:

public void populateDB(){
    XmlPullParserFactory pullParserFactory;
    ArrayList<Product> products = null;

    try {
        pullParserFactory = XmlPullParserFactory.newInstance();
        XmlPullParser parser = pullParserFactory.newPullParser();

        InputStream in_s = fContext.getApplicationContext().getAssets().open("products.xml");

        parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, false);
        parser.setInput(in_s, null);

        products =  parseXML(parser);

        String text = "";

        for(Product product:products)
        {

            text += "barcode : " + product.getBarcode() + " name : " + product.getName() + "\n";
        }

    } catch (XmlPullParserException e) {

        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }

    clearTable("products");
    ContentValues values = new ContentValues();
    for(int i = 0; i < products.size(); i++){
        values.clear();
        values.put("barcode", products.get(i).getBarcode());
        values.put("name", products.get(i).getName());
        values.put("itemcode", products.get(i).getItemcode());
        values.put("description", products.get(i).getDescription());

        insertProduct(values);
    }
}

And this is parseXML(), where I parse the file and generate a list of products.

private ArrayList<Product> parseXML(XmlPullParser parser) throws XmlPullParserException,IOException
{
    ArrayList<Product> products = null;
    int eventType = parser.getEventType();
    Product product = null;

    while (eventType != XmlPullParser.END_DOCUMENT){
        String name;
        switch (eventType){
            case XmlPullParser.START_DOCUMENT:
                products = new ArrayList();
                break;
            case XmlPullParser.START_TAG:
                name = parser.getName();
                if (name.equals("product")){
                    product = new Product();
                } else if (product != null){
                    if (name.equals("barcode")){
                        product.setBarcode(parser.nextText());
                    } else if (name.equals("name")){
                        product.setName(parser.nextText());
                    } else if (name.equals("itemcode")){
                        product.setItemcode(Integer.parseInt(parser.nextText()));
                    } else if (name.equals("description")){
                        product.setDescription(parser.nextText());
                    }
                }
                break;
            case XmlPullParser.END_TAG:
                name = parser.getName();
                if (name.equalsIgnoreCase("product") && product != null){
                    products.add(product);
                }
        }
        eventType = parser.next();
    }

    return products;

}

Now this works only with local files, but if I want to load it from a url? I tried the solution given in this thread, and this, this, this and this, but still it doesn't work.

It seems that the instruction parser.setInput(in_s, null); does not accept an inputstream containing an url.

The xml file path is the following: http://cendav.altervista.org/gestione_magazzino/products.xml

Davide Cenedese
  • 90
  • 1
  • 1
  • 9

1 Answers1

1

Normally I'll put in an asyncTask:

class getXMLResponseAsyncTask extends AsyncTask<String, Void, Boolean>{

        @Override
        protected void onPreExecute(){
         //do something
        }


        @Override
        public Boolean doInBackground(String... urls) {
            URL url;

            try {
                url = new URL(urls[0]);

                URLConnection connection = url.openConnection();

                DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
                DocumentBuilder builder = factory.newDocumentBuilder();
                Document doc = builder.parse(connection.getInputStream());


                NodeList nodes = doc.getElementsByTagName("products");
                for (int i = 0; i < nodes.getLength(); i++) {
                    Element element = (Element) nodes.item(i);
                    NodeList barcode = element.getElementsByTagName("barcode");
                    NodeList name = element.getElementsByTagName("name");
                    NodeList itemcode = element.getElementsByTagName("itemcode");



                    Element barcodeval = (Element) barcode.item(0);
                    Element nameval = (Element) name.item(0);
                    Element itemcodeval = (Element) itemcode.item(0);



                    String BARCODE = barcodeval.getTextContent();
                    String NAME  = nameval.getTextContent();
                    String ITEMCODE = itemcodeval.getTextContent();


                }


            } catch (MalformedURLException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            } catch (ParserConfigurationException e) {
                e.printStackTrace();
            } catch (SAXException e) {
                e.printStackTrace();
            }

            return false;
        }

        public void onPostExecute(Boolean result) {
        //do something
        }
    }

AND FINALLY YOU CAN USE IT ANYTIME YOU WANT

    new getXMLResponseAsyncTask().execute("http://cendav.altervista.org/gestione_magazzino/products.xml");
Orvenito
  • 412
  • 2
  • 14
  • This line `DocumentsContract.Document doc = builder.parse((connection.getInputStream()));` gives me the error of incopatible types. – Davide Cenedese Sep 15 '17 at 08:29
  • did you import `import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException;` ? – Orvenito Sep 15 '17 at 08:32
  • DocumentsContract.Document doc = builder.parse((connection.getInputStream())); Incopatible types: Required: android.provider.DocumentsConrtact.Document Found: org.w3c.dom.Document – Davide Cenedese Sep 15 '17 at 08:38
  • import these: `import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import org.xml.sax.SAXException;` – Orvenito Sep 15 '17 at 08:43
  • and make sure this line `Document doc = builder.parse(connection.getInputStream());` is is using it. – Orvenito Sep 15 '17 at 08:44
  • and remove this import `android.provider.DocumentsConrtact.Document` – Orvenito Sep 15 '17 at 08:46