Функция getDatabase () называется рекурсивной ошибкой? - PullRequest
0 голосов
/ 07 июля 2019

Я использую SQLiteDatabase для хранения данных, которые были куплены в фоновом режиме в методе AsyncTask doInBackground (), иногда, если полученные данные не были в базе данных, я вставляю данные, если полученные данные уже присутствовали и не прочитаны, я отмечаю, чтоданные как непрочитанные ... Но там написано, что getDatabase рекурсивно вызывается в методе doInBackground () ... Это проблема, потому что я выполнял операции в фоновом потоке или в некотором другом ... Это приложение извлекает новости с веб-сайта и отображает их в приложении, а такжедобавляет в базу данных sqlite, если новость была замечена, она помечается как старая ..

2019-07-07 16:16:46.664 27223-27276/com.github.chillmonk2.mycollege E/AndroidRuntime: FATAL EXCEPTION: AsyncTask #1
    Process: com.github.chillmonk2.mycollege, PID: 27223
    java.lang.RuntimeException: An error occurred while executing doInBackground()
        at android.os.AsyncTask$3.done(AsyncTask.java:365)
        at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:383)
        at java.util.concurrent.FutureTask.setException(FutureTask.java:252)
        at java.util.concurrent.FutureTask.run(FutureTask.java:271)
        at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:257)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
        at java.lang.Thread.run(Thread.java:784)
     Caused by: java.lang.IllegalStateException: getDatabase called recursively
        at android.database.sqlite.SQLiteOpenHelper.getDatabaseLocked(SQLiteOpenHelper.java:246)
        at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase(SQLiteOpenHelper.java:206)
        at com.github.chillmonk2.mycollege.NewsDbHelper.insertUrl(NewsDbHelper.java:36)
        at com.github.chillmonk2.mycollege.NewsDbHelper.onCreate(NewsDbHelper.java:26)
        at android.database.sqlite.SQLiteOpenHelper.getDatabaseLocked(SQLiteOpenHelper.java:310)
        at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase(SQLiteOpenHelper.java:206)
        at com.github.chillmonk2.mycollege.NewsDbHelper.urlExists(NewsDbHelper.java:59)
        at com.github.chillmonk2.mycollege.NewsFragment$TaskLoader.doInBackground(NewsFragment.java:144)
        at com.github.chillmonk2.mycollege.NewsFragment$TaskLoader.doInBackground(NewsFragment.java:111)
        at android.os.AsyncTask$2.call(AsyncTask.java:345)
        at java.util.concurrent.FutureTask.run(FutureTask.java:266)
        at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:257) 
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162) 
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636) 
        at java.lang.Thread.run(Thread.java:784) 

Вот класс Db Helper

package com.github.chillmonk2.mycollege;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

public class NewsDbHelper extends SQLiteOpenHelper {
   public static final String DATABASE_NAME = "news.db";
   public static final String TABLE_NAME = "newsIndex";
   public String COL_0 = "URL";
   public String COL_1 = "STATUS";
   SQLiteDatabase db;
   //SQLiteDatabase db = this.getWritableDatabase();
   public NewsDbHelper(Context context) {
       super(context, DATABASE_NAME, null ,1);
   }

   @Override
   public void onCreate(SQLiteDatabase db) {
       String createTable = " CREATE TABLE " + TABLE_NAME + "(" +
                           COL_0 + " TEXT PRIMARY KEY ," +
                           COL_1 + " INT );";
       db.execSQL(createTable);
       insertUrl("EMPTY");

   }

   @Override
   public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {

   }
   public int insertUrl(String url)
   {
       db = this.getWritableDatabase();
       ContentValues values = new ContentValues();
       values.put(COL_0,url);
       values.put(COL_1,"0");//0 - Unread
       int result = (int)db.insert(TABLE_NAME,null,values);
       return result;
   }
   public int updateUrl(String Url)
   {
       db = this.getWritableDatabase();
       ContentValues values = new ContentValues();
       values.put(COL_0,Url);
       values.put(COL_1,1);
       int result = db.update(TABLE_NAME,values,COL_0 +"=?",new String[]{Url});
       return result;
   }
   public int deleteUrl(String Url)
   {

       int result = db.delete(TABLE_NAME,COL_0 + "=?",new String[]{Url});
       return result;
   }
   boolean urlExists(String Url){
      db = this.getWritableDatabase();
       String sql = "select * from "+TABLE_NAME + " where "+ COL_0 +"=?";
       Cursor cursor = db.rawQuery(sql,new String[]{Url});
       int count = cursor.getCount();
       if (count>=1)
           return true;
       else
           return false;
   }
   int getUrlStatus(String url)
   {
       //SQLiteDatabase db = this.getWritableDatabase();
       String sql = "select "+COL_1+" from "+TABLE_NAME + " where "+ COL_0 +"=?";
       Cursor cursor = db.rawQuery(sql,new String[]{url});
       int status = -1;
       while (cursor.moveToFirst())
       {
           status = cursor.getInt(cursor.getColumnIndex(COL_1));
       }
       return status;
   }


}

Это часть кода в NewsFragment.javaкласс

 @Override
        protected ArrayList<NewsObject> doInBackground(Void... voids) {
            String url = "http://rvrjc.ac.in/";
            ArrayList<NewsObject> mList = new ArrayList<NewsObject>();
            Document document;
            try {
                Log.d(MainActivity.class.getSimpleName(),"Main Activity");
                document = Jsoup.connect(url).get();
                Elements lnews = document.select("ul.newsticker li b");
                Elements bnews = document.select("div#galleryimage p");
                //Get the title of the website
                for (Element news : lnews) {//latest news Section
                    String s = "New";
                    String descNews = news.select("p").text();
                    String newsUrl = news.select("a").attr("href");
                    if (newsUrl.startsWith("http")) {
                        //do nothing
                        if(!db.urlExists(newsUrl)){
                            db.insertUrl(newsUrl);
                        }
                        else
                        {
                            int status = db.getUrlStatus(newsUrl);
                            if(status==1){//read
                                s = "Old";
                            }
                            else
                                s = "New";
                        }
                       mList.add(new NewsObject(descNews, newsUrl,s));
                    } else
                        mList.add(new NewsObject(descNews, url ,s));
                }
                for(Element news:bnews){

                    String descNews = news.select("p").text();
                    String newsGif = news.select("p img").attr("src");
                    String newsStatus = "Old" ;
                    if(newsGif.equals("new.gif"))
                    {

                        newsStatus = "New";
                        //System.out.println("News Status changed");
                    }
                    String newsUrl = news.select("a").attr("href");
                    if(newsUrl.startsWith("http"))
                    {
                        if(!db.urlExists(newsUrl)){
                            db.insertUrl(newsUrl);
                        }
                        else
                        {
                            int status = db.getUrlStatus(newsUrl);
                            if(status==1){//read
                                newsStatus = "Old";
                            }
                            else
                                newsStatus = "New";
                        }
                        //do nothing
                        mList.add(new NewsObject(descNews,newsUrl,newsStatus));
                    }
                    else
                        mList.add(new NewsObject(descNews,url,newsStatus));
                }



            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            Log.e("TAG",""+mList);
            return mList;
        }
        @Override
        protected void onPostExecute(ArrayList<NewsObject> newsArrayList) {
            super.onPostExecute(newsArrayList);
            progressDialog.dismiss();
            Log.e("TAG","Inside onPostExecute"+newsArrayList);
            mNewsAdapter.addAll(newsArrayList);
            mNewsAdapter.notifyDataSetChanged();
        }
    }

1 Ответ

1 голос
/ 07 июля 2019

Строка

 insertUrl("EMPTY");

Причина, по которой вы пытаетесь использовать экземпляр NewsDbHelper для открытия базы данных, пока она еще находится на пути открытия базы данных.

  • Когда вы создаете экземпляр, база данных не открывается.Это не так, пока вы не попытаетесь получить доступ к базе данных, которая открыта.Именно во время этого открытия вызывается метод onCreate (если база данных ранее не существовала) для создания базы данных, поэтому вы не можете попытаться использовать this.getWritabaleDatabase, поскольку он все еще находится в процессе обработки другого this.getWritableDatabase ( или getReadableDatabase вместо getWritableDatabase )

Вместо этого вы можете использовать

db.execSQL("INSERT OR IGNORE INTO " + TABLE_NAME + "VALUES ('EMPTY',0)"); 
  • Примечание код в принципекод, он не был запущен или проверен и, следовательно, может содержать некоторые ошибки.
...