Autore Topic: Dove posizionare il database?  (Letto 975 volte)

Offline dariux

  • Nuovo arrivato
  • *
  • Post: 7
  • Respect: 0
    • Mostra profilo
  • Sistema operativo:
    Windows 8
Dove posizionare il database?
« il: 21 Giugno 2013, 18:17:38 CEST »
0
Salve a tutti.. ho un database sqlite popolato esterno all'applicazione e la corrispondente versione in file csv.. volevo sapere se c'è la possibilità di mettere il database all'interno di una cartella visibile da un OpenHelper.. l'idea che mi è venuta è quella di metterlo in assets ma da li mi da errore quando accedo con la classe SQLiteDatabase.. dovrei prima copiarlo all'interno dell'applicazione (/data/data/package/databases/..)
Inoltre mettendo il db in assets, è possibile che l'utente in qualche modo riesca a recuperare questo db ??

Tutte le idee sono ben accette.. Grazie in anticipo..

Offline rs94

  • Utente normale
  • ***
  • Post: 227
  • Respect: +21
    • Mostra profilo
  • Dispositivo Android:
    Sony Ericsson Xperia Arc S
  • Sistema operativo:
    Windows 8
Re:Dove posizionare il database?
« Risposta #1 il: 21 Giugno 2013, 23:19:26 CEST »
0
Una procedura corretta per fare ciò che tu dici (se ho capito bene cosa vuoi fare), è mettere il file del db già popolato nella cartella asset, e quindi spostarlo al primo avvio dell'app come database "normale". Da qui puoi accedere come fai normalmente con tutti i db sqlite su android.

Se metti il file in asset, avendo l'apk (facilmente recuperabile) è molto banale prendere il db: infatti basta un visualizzatore zip. Se il database contiene dati sensibili dovresti applicare qualche forma di protezione
L'unica certezza è il dubbio.
Dubitare di se stessi è il primo segno di intelligenza.

Offline dariux

  • Nuovo arrivato
  • *
  • Post: 7
  • Respect: 0
    • Mostra profilo
  • Sistema operativo:
    Windows 8
Re:Dove posizionare il database?
« Risposta #2 il: 21 Giugno 2013, 23:58:15 CEST »
0
ti ringrazio... per importare da asset a db "normale" cosa mi consigli di usare?? sempre un sqliteopenhelper?? adesso provo al limite a prendere un altra strada cioè quella di mettere il db in rete ed importarlo all'avvio (probabilmente per ciò che devo fare io è meno problematico)..
cmq nel caso invece mettessi i dati su una classe java anche questa è esposta a problemi di sicurezza come il database?? in teoria una volta compilato nell'apk c'è bytecode (i file class) quindi non si dovrebbe vedere o recuperare.. questo giusto per curiosità
Grazie.

Offline daveblack

  • Nuovo arrivato
  • *
  • Post: 43
  • Respect: 0
    • http://www.linkedin.com/profile/view?id=155824415&trk=tab_pro
    • Mostra profilo
    • DC Hall
  • Dispositivo Android:
    Samsung Galaxy Next
  • Sistema operativo:
    Mac OSX 10.7 Lion
Re:Dove posizionare il database?
« Risposta #3 il: 22 Giugno 2013, 10:54:11 CEST »
0
Non so cosa tu stia facendo, ma se vuoi proteggere i dati ti conviene lavorare con un server esterno su cui carichi il DB.
Per farti un esempio: io ed altri 2 siamo riusciti a recuperare il DB delle fermate dei treni dall'app "ProntoTreno" su iOS... e se ce l'abbiamo fatta noi, ce la fa chiunque.

Offline rs94

  • Utente normale
  • ***
  • Post: 227
  • Respect: +21
    • Mostra profilo
  • Dispositivo Android:
    Sony Ericsson Xperia Arc S
  • Sistema operativo:
    Windows 8
Re:Dove posizionare il database?
« Risposta #4 il: 22 Giugno 2013, 14:30:23 CEST »
0
Se ti serve la protezione dei dati il problema si fa più complesso, perchè un "semplice" db non va più bene.
La soluzione più facile è fare una crittografia dei dati tramite un algoritmo, ad esempio AES. Quindi a runtime li decripti.
Un altro modo sarebbe cittografare l'intero db, e all'apertura dell'app fare la decrittazione.

Anche se fai un db lato server, e poi ci accedi tramite l'app, i problemi non sono risolti. Infatti:
1- l'app richiede connessione ad internet, se puoi farne a meno inserendo il db già dentro l'app è meglio
2- comunque analizzando il bytecode si può risalire all'indirizzo da cui prelevi il db e scaricarlo "tranquillamente". Ovviamente è più difficile che prenderlo dall'apk ma non è impossibile.
L'unica certezza è il dubbio.
Dubitare di se stessi è il primo segno di intelligenza.

Offline daveblack

  • Nuovo arrivato
  • *
  • Post: 43
  • Respect: 0
    • http://www.linkedin.com/profile/view?id=155824415&trk=tab_pro
    • Mostra profilo
    • DC Hall
  • Dispositivo Android:
    Samsung Galaxy Next
  • Sistema operativo:
    Mac OSX 10.7 Lion
Re:Dove posizionare il database?
« Risposta #5 il: 22 Giugno 2013, 14:54:57 CEST »
0
2- comunque analizzando il bytecode si può risalire all'indirizzo da cui prelevi il db e scaricarlo "tranquillamente". Ovviamente è più difficile che prenderlo dall'apk ma non è impossibile.

Non sono d'accordo, io per esempio quando devo scaricare dati sensibili (coordinate GPS e simili), interrogo uno script PHP su un server esterno che esegue query sul DB... in questo modo il telefono scarica solo i dati che gli servono... Non è possibile scaricare tutto il DB.

Offline rs94

  • Utente normale
  • ***
  • Post: 227
  • Respect: +21
    • Mostra profilo
  • Dispositivo Android:
    Sony Ericsson Xperia Arc S
  • Sistema operativo:
    Windows 8
Re:Dove posizionare il database?
« Risposta #6 il: 22 Giugno 2013, 15:07:42 CEST »
0
Però avendo l'indirizzo dello script in php e i vari parametri (ottenibili dal bytecode dell'app), è abbastanza facile fare un programmino che scarica i dati cambiando di volta in volta i parametri e li inserisce in un db in locale. Non dico che sia facile, ma la sicurezza non è certa neanche con un server esterno.

Idee personali comunque :D
L'unica certezza è il dubbio.
Dubitare di se stessi è il primo segno di intelligenza.

Offline tafazzi87

  • Nuovo arrivato
  • *
  • Post: 31
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    Google nexus 7 - acer E330
  • Sistema operativo:
    Ubuntu 12.04 - Mac OS X 10.6.8
Re:Dove posizionare il database?
« Risposta #7 il: 24 Giugno 2013, 15:08:57 CEST »
0
io ho più o meno lo stesso problema...ho un db sqlite che ho messo in assets già popolato, tramite questa guida http://www.reigndesign.com/blog/using-your-own-sqlite-database-in-android-applications/ ho avuto accesso al db.
sull'emulatore funziona tutto bene ma quando lo faccio partire sul device non funziona, c'è qualche posizione precisa dove mettere il db all'interno del device?

Offline rs94

  • Utente normale
  • ***
  • Post: 227
  • Respect: +21
    • Mostra profilo
  • Dispositivo Android:
    Sony Ericsson Xperia Arc S
  • Sistema operativo:
    Windows 8
Re:Dove posizionare il database?
« Risposta #8 il: 25 Giugno 2013, 11:18:07 CEST »
0
Posta il codice e il logcat
L'unica certezza è il dubbio.
Dubitare di se stessi è il primo segno di intelligenza.

Offline tafazzi87

  • Nuovo arrivato
  • *
  • Post: 31
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    Google nexus 7 - acer E330
  • Sistema operativo:
    Ubuntu 12.04 - Mac OS X 10.6.8
Re:Dove posizionare il database?
« Risposta #9 il: 25 Giugno 2013, 12:01:16 CEST »
0
MainActivity.java
Codice (Java): [Seleziona]
package pack.pullman;

import java.io.IOException;
import java.sql.SQLException;
import java.util.List;

import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Marker;
import com.google.android.gms.maps.model.MarkerOptions;

import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.view.Menu;
import android.widget.Toast;

public class MainActivity extends FragmentActivity {
        private GoogleMap map;
        private DataSource db;
        private MyOpenHelper o;
        public LatLng adesso;
        @Override
        protected void onCreate(Bundle savedInstanceState) {
                super.onCreate(savedInstanceState);
                setContentView(R.layout.activity_main);
                o=new MyOpenHelper(this);
                try{
                        o.createDataBase();
                }catch (IOException e){
                        throw new Error("Non posso creare il database");
                }
                try{
                o.openDataBase();}
                catch (SQLException e){
                        e.printStackTrace();
                }
        db=new DataSource(o);
                crea();
                LocationManager location=(LocationManager) getSystemService(getApplicationContext().LOCATION_SERVICE);
                final List<Coordinate> lista=db.vediCoordinate();
                LocationListener listenergps=new LocationListener() {
                       
                        @Override
                        public void onStatusChanged(String provider, int status, Bundle extras) {
                                // TODO Auto-generated method stub
                       
                        }
                       
                        @Override
                        public void onProviderEnabled(String provider) {
                                // TODO Auto-generated method stub
                                Toast.makeText(getApplicationContext(),"Gps Attivo", Toast.LENGTH_LONG).show();
                               
                        }
                       
                        @Override
                        public void onProviderDisabled(String provider) {
                                // TODO Auto-generated method stub
                                Toast.makeText(getApplicationContext(),"Gps Disattivato, ATTIVALO!!!!", Toast.LENGTH_LONG).show();
                               
                        }
                       
                        @Override
                        public void onLocationChanged(Location location) {
                                // TODO Auto-generated method stub
                                List<LatLng> vicini=db.piuvicino(location, lista);
                                adesso=new LatLng(location.getLatitude(), location.getLongitude());
                                Marker posizione=map.addMarker(new MarkerOptions().position(adesso).title("Sei Qui"));
                                Marker a[]=new Marker[vicini.size()];
                                for(int i=0;i<vicini.size();i++){
                                        a[i]=map.addMarker(new MarkerOptions().position(vicini.get(i)));
                                }
                        map.moveCamera(CameraUpdateFactory.newLatLngZoom(adesso, 15));
                        map.animateCamera(CameraUpdateFactory.zoomTo(20),2000,null);
                        }
                };
               
        }

        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
                // Inflate the menu; this adds items to the action bar if it is present.
                getMenuInflater().inflate(R.menu.main, menu);
                return true;
        }
        public void crea(){
                map=((SupportMapFragment)getSupportFragmentManager().findFragmentById(R.id.mappa)).getMap();           
        }
}
DataSource.java
Codice (Java): [Seleziona]
package pack.pullman;

import java.util.LinkedList;
import java.util.List;

import com.google.android.gms.maps.model.LatLng;

import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.location.Location;

public class DataSource {
        private MyOpenHelper oh;
        private Cursor cu;
        public DataSource(MyOpenHelper o){
                oh=o;
        }
        public List<Coordinate> vediCoordinate(){
                SQLiteDatabase db=oh.getReadableDatabase();
                String c[]=new String[]{"lat","long","via"};
                cu=db.query("linee", c, null, null, null, null, null);
                int rows=cu.getCount();
                LinkedList<Coordinate> risultato=new LinkedList<Coordinate>();
                cu.moveToFirst();
                for(int i=0;i<rows;i++){
                        risultato.add(i,new Coordinate(cu.getDouble(cu.getColumnIndex("lat")),cu.getDouble(cu.getColumnIndex("long")),cu.getString(cu.getColumnIndex("via"))));
                        cu.moveToNext();
                }
                cu.close();
                return risultato;      
        }
        public List<LatLng> piuvicino(Location l,List<Coordinate> a){
                float results[]=new float[a.size()];
                LinkedList<LatLng> lista=new LinkedList<LatLng>();
                for(int i=0;i<a.size();i++){
                        Location.distanceBetween(l.getLatitude(), l.getLongitude(), a.get(i).getLatitudine(), a.get(i).getLongitudine(), results);
                }
                for(int i=0;i<results.length;i++){
                        if(results[i]<200){
                                lista.add(new LatLng(a.get(i).getLatitudine(), a.get(i).getLongitudine()));
                        }
                }
                return lista;
        }
}
MyOpenHelper.java
Codice (Java): [Seleziona]
package pack.pullman;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.sql.SQLException;


import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteException;
import android.database.sqlite.SQLiteOpenHelper;

public class MyOpenHelper extends SQLiteOpenHelper{
                 
            //The Android's default system path of your application database.
            private static String DB_PATH = "/data/data/pack.pullman/databases/";
         
            private static String DB_NAME = "orari";
         
            private SQLiteDatabase myDataBase;
         
            private final Context myContext;
         
            /**
             * Constructor
             * Takes and keeps a reference of the passed context in order to access to the application assets and resources.
             * @param context
             */

            public MyOpenHelper(Context context) {
                super(context, DB_NAME, null, 1);// 1? its Database Version
                if(android.os.Build.VERSION.SDK_INT >= 4.2){
                    DB_PATH = context.getApplicationInfo().dataDir + "/databases/";        
                } else {
                   DB_PATH = "/data/data/" + context.getPackageName() + "/databases/";
                }
                this.myContext = context;
            }  
         
          /**
             * Creates a empty database on the system and rewrites it with your own database.
             * */

            public void createDataBase() throws IOException{
         
                boolean dbExist = checkDataBase();
         
                if(dbExist){
                        //do nothing - database already exist
                }else{
         
                        //By calling this method and empty database will be created into the default system path
                       //of your application so we are gonna be able to overwrite that database with our database.
                        this.getReadableDatabase();
         
                        try {
         
                                copyDataBase();
                               
         
                        } catch (IOException e) {
         
                                throw new Error("Error copying database");
         
                        }
                }
         
            }
         
            /**
             * Check if the database already exist to avoid re-copying the file each time you open the application.
             * @return true if it exists, false if it doesn't
             */

            private boolean checkDataBase(){
         
                SQLiteDatabase checkDB = null;
         
                try{
                        String myPath = DB_PATH + DB_NAME;
                        checkDB = SQLiteDatabase.openDatabase(myPath, null, SQLiteDatabase.OPEN_READWRITE);
         
                }catch(SQLiteException e){
         
                        //database does't exist yet.
         
                }
         
                if(checkDB != null){
         
                        checkDB.close();
         
                }
         
                return checkDB != null ? true : false;
            }
         
            /**
             * Copies your database from your local assets-folder to the just created empty database in the
             * system folder, from where it can be accessed and handled.
             * This is done by transfering bytestream.
             * */

            private void copyDataBase() throws IOException{
         
                //Open your local db as the input stream
                InputStream myInput = myContext.getAssets().open(DB_NAME);
         
                // Path to the just created empty db
                String outFileName = DB_PATH + DB_NAME;
         
                //Open the empty db as the output stream
                OutputStream myOutput = new FileOutputStream(outFileName);
         
                //transfer bytes from the inputfile to the outputfile
                byte[] buffer = new byte[1024];
                int length;
                while ((length = myInput.read(buffer))>0){
                        myOutput.write(buffer, 0, length);
                }
         
                //Close the streams
                myOutput.flush();
                myOutput.close();
                myInput.close();
         
            }
         
            public void openDataBase() throws SQLException{
         
                //Open the database
                String myPath = DB_PATH + DB_NAME;
                myDataBase = SQLiteDatabase.openDatabase(myPath, null, SQLiteDatabase.OPEN_READWRITE);
               
         
            }
         
            @Override
                public synchronized void close() {
         
                    if(myDataBase != null)
                            myDataBase.close();
         
                    super.close();
         
            }
                @Override
                public void onCreate(SQLiteDatabase db) {
                        // TODO Auto-generated method stub
                       
                }

                @Override
                public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
                        // TODO Auto-generated method stub
                       
                }
         
                // Add your public helper methods to access and get content from the database.
               // You could return cursors by doing "return myDataBase.query(....)" so it'd be easy
               // to you to create adapters for your views.
         
        }
LOGCAT
Codice: [Seleziona]
06-25 11:58:37.894: E/SqliteDatabaseCpp(10049): sqlite3_open_v2("/data/data/pack.pullman/databases/orari", &handle, 2, NULL) failed
06-25 11:58:37.904: E/SQLiteDatabase(10049): Failed to open the database. closing it.
06-25 11:58:37.904: E/SQLiteDatabase(10049): android.database.sqlite.SQLiteCantOpenDatabaseException: unable to open database file
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.database.sqlite.SQLiteDatabase.dbopen(Native Method)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:1013)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:986)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:962)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at pack.pullman.MyOpenHelper.checkDataBase(MyOpenHelper.java:79)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at pack.pullman.MyOpenHelper.createDataBase(MyOpenHelper.java:45)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at pack.pullman.MainActivity.onCreate(MainActivity.java:33)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.Activity.performCreate(Activity.java:4465)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1049)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1920)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1981)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.ActivityThread.access$600(ActivityThread.java:123)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1147)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.os.Handler.dispatchMessage(Handler.java:99)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.os.Looper.loop(Looper.java:137)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at android.app.ActivityThread.main(ActivityThread.java:4424)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at java.lang.reflect.Method.invokeNative(Native Method)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at java.lang.reflect.Method.invoke(Method.java:511)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:787)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:554)
06-25 11:58:37.904: E/SQLiteDatabase(10049):         at dalvik.system.NativeStart.main(Native Method)

Post unito: 25 Giugno 2013, 13:01:15 CEST
il file del database si chiama orari ed è all'interno di assets
« Ultima modifica: 25 Giugno 2013, 13:01:15 CEST da tafazzi87, Reason: Merged DoublePost »