mecanismos de persistencia en android

Post on 13-Jun-2015

1.843 Views

Category:

Technology

2 Downloads

Preview:

Click to see full reader

DESCRIPTION

La persistencia es un detalle imprescindible en la mayoría de aplicaciones. En esta charla se dará una visión de distintos mecanismos para persistir los datos en aplicaciones Android. Se hará especial énfasis en el uso de patrones de diseño para implementar la persistencia de manera que se incremente la flexibilidad y mantenibilidad de nuestras aplicaciones. La charla estará acompañada de ejemplos prácticos de código para ilustrar los principios descritos.

TRANSCRIPT

1

Mecanismos de Persistencia en

Android

Febrero 2014

Javier Muñoz Ferrara jmunoz@grupogimeno.com http://twitter.com/jmunozf

http://www.linkedin.com/in/javiermf

2

§  Holding familiar. 3ª Generación

§  Más de 30 empresas.

§  Con 2.500 empleados.

§  Presente en 9 Comunidades.

§  Dando servicio a más de 1 millón de personas.

La empresa

3

La empresa

GSC

Área Software

4

Área DataCenter y Comunic. Área de Microinf.

DEPARTAMENTO DE T.I.C.

28 personas

La empresa

Desarrollos a medidas en entornos VB y Java

Proyectos de movilidad Android

Web Responsive

Desarrollos Web: Intranets corporativas

Extranets

Portales webs

Gestión Documental

Sist. de información Geográfica (GIS)

SAP R3 – BI/BO

Administración de servidores y BBDD.

Virtualización de servidores

Gestión de comunicaciones y radioenlaces/WIFI

Cloud privado - CPD propio (Tier III)

Mantenimiento integral

microinformático.

Asistencia remota

Soporte online

Auditorias del parque tecnológico.

Soporte de Helpdesk

Externalización de equipos de

impresión.

Venta de material informático

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

Almacenar los datos de la aplicación

para que estén disponibles al reiniciar

el software

Conceptos básicos ¿Qué es la persistencia?

Las aplicaciones se reinician

La RAM es limitada

Conceptos básicos ¿Por qué es necesaria?

Conceptos básicos ¿Es importante?

La persistencia suele ser imprescindible

para el correcto funcionamiento de las

aplicaciones

Conceptos básicos ¿Es LO MÁS importante?

NO. Lo más importante son las reglas

de negocio de los usuarios/clientes

¿Entonces por qué muchas veces empezamos

diseñando e implementando la base de datos?

Conceptos básicos ¿Cómo persistir los datos?

Al usuario/cliente probablemente no le interese

BBDD NoSQL

BBDD Relacionales Archivos Binarios

CSV

XML

Almacenamiento Cloud Servicios Web

Conceptos básicos ¿Cómo persistir los datos?

¿Cómo podemos persistir en Android?

§  Preferencias §  Parejas: clave -> valor

§  Configuraciones, recordar acciones, etc.

§  Almacenamiento de archivos §  Almacenamiento interno o externo

§  Archivos arbitrarios (imágenes, json, xml, texto, binarios, etc.)

§  Datos estructurados §  Base de datos SQL

§  Colecciones de datos estructurados y relacionados

Tipo de Persistencia ¿Cómo realizar la persistencia en móvil?

Local §  Almacenamiento en el propio móvil

§  Especio limitado. Acceso rápido. Alto coste consultas complejas

1.-

Tipo de Persistencia ¿Cómo realizar la persistencia en móvil?

Remota en un servidor §  El móvil sólo muestra datos, que lee de un servidor

§  Cada acceso a datos requiere un consulta

§  Alta latencia. Muy sensible a desconexiones

2.-

Tipo de Persistencia ¿Cómo realizar la persistencia en móvil?

Mix (Cacheo/Hoarding) §  Copia local de alguna información del servidor

§  Comunicación con el servidor para sincronizar

§  Funcional (más o menos) desconectado. Latencia según acierto.

3.-

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

Retos Espacio limitado

Almacenamiento local §  Memoria interna/Memoria externa

§  Varios GB (no está mal)

Seleccionar datos a persistir

Retos Computación y memoria limitada

Consultas complejas lentas §  Mejor preprocesar datos en el servidor

§  Desnormalizar BBDD si es posible

Alto consumo de batería

Retos Restricciones de comunicación

Dificultad para sincronizar §  Minimizar número de conexiones

§  Sólo datos relevantes para la aplicación

§  Sólo modificaciones a los datos

§  Preprocesar datos

Retos Desconexiones habituales

Modo off-line. ¿Qué ocurre? §  No funciona nada

§  Funcionamiento limitado (sólo lectura)

§  Funcionamiento completo (conflictos)

Recuperación conexión §  Sincronización de datos

§  Resolución de conflictos

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

El camino sin reflexionar

Diseñar y crear la BBDD

Escribir SQL donde haga falta leer o modificar datos

Utilizar cursores para recorrer los resultados

Con el paso del tiempo

¿Y si cambio el nombre o tipo de una columna?

¿Y si añado una tabla nueva?

¿Y si cambio BBDD local por servicios web externos?

Diseño de la persistencia

Originario del ámbito J2EE

Aplicable a cualquier tipo de software OO

Patron DAO Data Access Object

Patrón DAO ¿Qué es?

Interfaz con métodos de persistencia para Bussiness Objects

Independiente del mecanismo de persistencia (BBDD, XML, Servicios

Web, etc.)

Sólo entran y salen Bussiness Objects y tipos primitivos

Excepciones independientes de la persistencia

Patrón DAO ¿Qué es?

Entran y salen objetos, pero la lógica de la aplicación no

sabe cómo se guardan

Patrón DAO Beneficios e Inconvenientes

Separación lógica aplicación y gestión persistencia

Evolución/Migración persistencia sin cambiar lógica aplicación

Centralización de las tareas de persistencia (mejor mantenimiento)

Capa extra quizá innecesaria en aplicaciones pequeñas

Mueve objetos enteros -> Sobrecarga (si no se diseña bien)

Dificulta integración con frameworks ActiveRecord u ORM

Beneficios

Inconvenientes

Patrón DAO Estructura habitual

Un objeto DAO por Bussiness Object/Tabla

Métodos habituales en el interfaz List<BO> getAll() / findAll()

BO getById(Long id) / findById(Long id)

insert(BO theObject)

delete(BO theObject)

update(BO theObject)

Y todos los que hagan falta….

Patrón DAO Métodos Genéricos vs Métodos Específicos

Ejemplo: Aplicación tipo Google Calendar (vista calendario + vista detalle)

Métodos genéricos List<Event> getAllEvents()

Event insertEvent(Event e)

Event updateEvent(Event e)

Métodos genéricos

List<Event> getAllEventsWithScheduleInfo()

updateScheduleInfo(long eventId, Date start, Date end)

Event insertEvent(String title, Date start, Date end)

Event getEventWithDetailnfo()

Event updateEvent(Event e)

DAO permite varias persistencias. ¿Para qué?

Conectado vs Desconectado

Desarrollo vs Producción

Lite vs Premium

Conexión rápida vs Conexión lenta

¿Cómo cambiar entre persistencias?

UsuariosDAO usuariosDAO = new UsuariosSQliteDAO();

UsuariosDAO usuariosDAO = new UsuariosRESTDAO();

¡Disperso por toda la aplicación!

¿Cómo cambiar de persistencia?

Patrón DAO Abstract Factory Pattern

Factoría -> encargado de crear objetos

Agrupar y encapsular factorías individuales (una por DAO)

DAOFactory

getUsersDAO() getProducsDAO()

SqliteDAOFactory

getUsersDAO() getProducsDAO()

RestDAOFactory

getUsersDAO() getProducsDAO()

<implementa>

UserSqliteDAO ProductsSqliteDAO

UserRestDAO ProductsRestDAO

Patrón DAO Abstract Factory Pattern

DAOFactory

getUsersDAO() getProducsDAO()

SqliteDAOFactory

getUsersDAO() getProducsDAO()

RestDAOFactory

getUsersDAO() getProducsDAO()

<implementa>

MyAppDAOFactory

getUsersDAO() getProducsDAO()

<delega en> <delega en>

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

Android Annotations ¿Por qué utilizarlo?

Facilitar la legibilidad del código

Evitar escribir código boilerplate

Centrarse en la lógica de la aplicación

Ocultar la complejidad técnica

Android Annotations ¿Qué funcionalidad simplifica?

Inyección de dependencias §  Obtener referencias a vistas, recursos, extras, etc.

Gestión de threads §  UI vs Background

Listeners de eventos §  No más clases anónimas

Cliente REST §  Interacción con servicios WEB

Android Annotations ¿Cómo funciona?

Anotaciones Java

Generación automática de código boilerplate

Clases que extienden las de la aplicación

Necesario referencias las clases generadas

Android Annotations Ejemplo

SQLite en Android Conceptos básicos

Incluida en por defecto Open Source → Utilizada en otros muchos proyectos

Ligera y embebida

BDs privadas de cada aplicación

Se almacenan en “/data/data/<package-name>/databases”

A tener en cuenta No mantiene integridad de datos

No mantiene integridad referencial (foreign keys) Se puede simular con triggers

Por defecto no tiene soporte completo a Unicode

No proporciona interfaz gráfica de administración

SQLite en Android Implementación

Crear clase para administración: Heredar de android.database.sqlite.SQLiteOpenHelper

Parámetros del constructor: Contexto Nombre de la DB CursorFactory (null para utilizar el por defecto) Versión del esquema de BBD (para tener en cuenta en migraciones)

Implementar métodos de construcción

public void onCreate(SQLiteDatabase db) {

db.execSQL("CREATE TABLE "+tableName+" (_id INTEGER PRIMARY KEY , "+

colDeptName+ " TEXT)");

// More stuff including initial data

}

SQLite en Android Implementación

Implementar método de migración Parámetros del constructor:

oldVersion: versión de la bbdd en el dispositivo newVersion: versión que se quiere alcanzar

Desde la Actividad:

Crear instancia del DBOpenHelper Conseguir DB

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

// do stuff

}

db.getWritableDatabase();

SQLite en Android Interactuando con la BBDD

Consultas (Queries) Modo “raw”:

Modo “sencillo” (API)

SQLiteDatabase db=this.getReadableDatabase();

Cursor cur=db.rawQuery("SELECT "+colDeptID+" as _id,"+colDeptName+" from "+deptTable,new String [] {});

SQLiteDatabase db=this.getReadableDatabase();

String [] columns=new String[]{"_id",colName,colAge,colDeptName};

Cursor c=db.query(viewEmps, columns, colDeptName+"=?",

new String[]{Dept}, null, null, null);

§  Nombre tabla §  Columnas §  Condición WHERE

§  Argumentos del WHERE §  Cláusula GROUP BY §  Clásula HAVING

§  Clásulula ORDER BY

SQLite en Android Interactuando con la BBDD

Insertar fila SQLiteDatabase db=this.getWritableDatabase();

ContentValues cv=new ContentValues();

cv.put(“colDeptID”, 1);

cv.put(“colDeptName”, "Sales");

db.insert(deptTable, “colDeptID”, cv);

cv.put(“colDeptID”, 2);

cv.put(“colDeptName”, "IT");

db.insert(“tablename”, null, cv);

db.close();

SQLite en Android Operaciones con Vectores

Puntero a un conjunto de datos Resultado de una interacción con una BBDD

Operaciones de gestión:

close() deactivate() requery()

Operaciones de consulta: getInt(int column_index) getString(int column_index) Etc. getColumnIndex(String

ColumnName)

Operaciones de posición: moveToNext() moveToFirst()

moveToPosition(int pos)

moveToLast()

isFirst()

isLast()

isBeforeFirst()

isAfterLast()

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

Una técnica de programación para

convertir datos entre un sistema OO y un

sistema Relacional

Object-Relational Mapping ¿Qué es un ORM?

Object-Relational Mapping Impedancia Objeto-Relacional

Relacional Tablas

Orientación a Objetos Grafos

Gestionan la impedancia OO-Relacional

Aplican patrones estándar de correspondencia

OK para el 90% de la funcionalidad necesaria

Object-Relational Mapping Frameworks ORM

Object-Relational Mapping Algunas Recomendaciones

Loggea y lee las SQL que genera el ORM

Utiliza profiling para encontrar queries lentas

Añade los selects para recuperar sólo columnas necesarias

Utiliza raw SQL cuando el ORM complica las cosas

OrmLite ¿Qué es?

http://ormlite.com/

ORM básico para aplicaciones Java

Se integra con MySQL, PostgreSQL, SQL Server, SQLite…

Mapping por anotaciones

Generación dinámicas de DAOs básicos

OrmLite Definició de las correspondiencias

@DatabaseTable(tableName = "samples") public class SampleRow { […] @DatabaseField(columnName = COLUMN_ID, id = true) String id; @DatabaseField(foreign = true, columnName = COLUMN_ROUTEPLANED) RouteRow routeRowPlannedSample; @DatabaseField(foreign = true, foreignAutoRefresh = true) UserRow madeByRow; @DatabaseField(foreign = true, foreignAutoRefresh = true) UserRow takenByRow; @DatabaseField(columnName = COLUMN_KIND) SampleKind kind; @DatabaseField(columnName = COLUMN_CITYNAME) String cityName; @DatabaseField(columnName = COLUMN_COMMENTSFORANALYST) String comment; @ForeignCollectionField(eager = false) public ForeignCollection<SampleParameterRow> samplesParameters; […] }

OrmLite Manipular la BBDD

Instanciar el OpenHelper

Obtener un DAO para un tipo de objeto

@RootContext Context ctxt; Dao<SampleRow, Long> dbDAO; @AfterInject void initDbHelper() { DatabaseHelper dbHelper = OpenHelperManager.getHelper(ctxt, DatabaseHelper.class); try { dbDAO = dbHelper.getDao(SampleRow.class); } catch (SQLException e) { dbDAO = null; } }

OrmLite Manipular la BBDD

Crear un objeto

SampleRow sampleRow = new SampleRow(); sampleRow.setCityName(“Zaragoza”); […] dbDAO.create(sampleRow);

sampleRow.setCityName(“Huesca”); //debe tener id dbDAO.update(sampleRow);

Actualizar un objeto

dbDAO.delete(sampleRow); // o también dbDAO.deleteById(sampleRow.getId());

Eliminar un objeto

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

Servicios de persistencia de manera remota

a través de Internet

Persistencia Cloud ¿Qué es?

Servicios Cloud Ventajas e Inconvenientes

Evitar infraestructura sobredimensionada

Evitar costes de administración y mantenimiento

Distribuir costes en el tiempo

Soportar picos de necesidad

Problemas de privacidad y seguridad

Imposible adaptación/personalización

Difícil respuesta a fallos de servicio

Falta de estándares (vendor lock-in)

Ventajas

Inconvenientes

Persistencia Cloud Ecosistema de Servicios

Acceso por SDK o API REST

SimpleDB (REST + SDK)

MongoDB (REST)

Oracle (custom REST)

Parse Data (REST + SDK)

CouchDB (SDK)

Firebase Data (REST + SDK)

Sistemas de almacenamiento de información que

no cumplen con el esquema entidad-relación

NoSQL ¿Qué es?

No hay consultas con SQL

No hay estructura fija

No hay JOINs

No garantizan ACID (atomicidad, coherencia, aislamiento y durabilidad)

NoSQL ¿Por qué surge?

Aplicaciones Web Globales

- Grandes volúmenes

- Datos heterogéneos

- Rápida evolución de la estructura

- Acceso escalable

Nueva Infraestructura

- Grandes clústers

- Almacenamiento y computación cloud

NoSQL ¿Por qué surge?

Problemas de BBDD Relacionales

- No escalan bien en horizontal (distribución)

- Dificultan las evolución del esquema

Persistencia “Políglota”

- Distintas necesidades -> Distinto tipo de persistencia

- Encapsular para independizar

Datos muy estructurados Volumen reducido Acceso ocasional

Datos poco estructurados Volumen muy grande Acceso constante

Características NoSQL

Schema-less

Facilidades distribución

Consistencia ocasional

Características NoSQL Principales tipos de BBDD NoSQL

Clave->Valor - Como un map enorme

- Particionado sencillo por clave

Document Store - Mapas anidados con listas

- Permiten “consultas” del contenido

Big Table - Filas y columnas

- “Familias” de columnas dinámicas

BBDD Grafos

- Nodos, propiedades y aristas

- Permiten consultas complejas

NoSQL Ventajas e Inconvenientes

Estructura adecuada para algunos datos

Mejor escalabilidad

Más flexibilidad de la estructura de datos

Aplicaciones más complejas

Falta de estandarización/formación

Integración estrategias persistencia

Ventajas

Inconvenientes

Parse Conceptos Básicos

Parse Data - Parte de suite de servicios para desarrollo de apps

- Notificaciones PUSH, Identificación, Analíticas…

Instalación

1.- Descargar JAR e incluir

2.- Inicializar librería

Parse.initialize(this, APP_CODE, API_KEY);!

Parse Manipular datos

Guardar datos

Consultas

ParseObject parseObject = new ParseObject("Note");!

parseObject.put("title",note.getTitle());!

parseObject.put("text",note.getText());!

parseObject.put("category",ParseObject.createWithoutData("Category",note.getCategory().getId()));!

!

ParseQuery<ParseObject> query = ParseQuery.getQuery("Note"); !

for (ParseObject parseObject : query.find()) { …. }!

!

ParseObject parseObject = query.get(noteToEditId);!

¿Qué es persistencia?

Retos de la persistencia en móviles

¿Cómo diseñar la persistencia de datos?

Mecanismos de persistencia de datos en Android

SQLite

ORMLite

Parse

Servicios REST

Índice

El Representational State Transfer (REST)

es un estilo arquitectónico para sistemas

software distribuidos basado en

RECURSOS

REST ¿Qué es?

Cliente <- Recurso -> Servidor

REST ¿Qué es?

BBDD API REST

Aplicación Software

RECURSO

Cualquier concepto con significado en la

aplicación que puede ser nombrado

REST Recursos

CLIENTE FACTURA

LUGAR

TIENDA COMENTARIO

Basado en URLs (Human readable)

Recomendaciones:

REST Nombrado

http://example.com/customers/1234 http://example.com/orders/2007/10/776654/products http://example.com/bills/4554/lines/6

recurso subrecurso

- No utilizar nombres de acción -  Evitar parámetros (si es posible)

-  Denominación en plural

Acciones estándar definidas en HTTP

REST Acciones

Comando HTTP Acción Código

respuesta Contenido respuesta

GET Lectura Código 200 (OK)

El recurso/s consultado/s

POST Creación Código 201 (Created) El recurso creado

PUT Modificación Código 200 (OK)

El recurso modificado

DELETE Eliminación Código 204 (No content) Nada

Representación en texto del recurso (human-readable)

- JSON, XML, HTML, YAML, RSS, ATOM

REST Representación

JSON XML

q  Leer un stream

REST Conexión HTTP manual

String getURL = “http://nombredelservidor.com/services/clientes/”+clienteId;

URL url = new URL(myurl);

HttpURLConnection conn = (HttpURLConnection) url.openConnection();

conn.setReadTimeout(10000 /* milliseconds */);

conn.setConnectTimeout(15000 /* milliseconds */);

conn.setRequestMethod("GET");

conn.setDoInput(true);

// Starts the query

conn.connect();

int response = conn.getResponseCode();

is = conn.getInputStream();

JSONObject clienteJsonObject = new JSONObject(is.toString());

ObjectMapper mapper = new ObjectMapper();

return mapper.readValue(clienteJsonObject, Cliente.class);

q  Definir una interfaz

REST Con Android Annotations

@Rest(rootUrl = "http://nombredelservidor.com/services/",converters = { MappingJacksonHttpMessageConverter.class })

public interface ClientesClient {

@Get(”clientes/{clientId}")

Client getClienteById(String clientId);

}

La persistencia es un detalle (importante)

Varias opciones/tecnologías de implementación

Elija una, pero no hipoteques tu futuro

Mecanismos de Persistencia en Android Conclusiones

74

Mecanismos de Persistencia en Android

Javier Muñoz Ferrara jmunoz@grupogimeno.com http://twitter.com/jmunozf

http://www.linkedin.com/in/javiermf

top related