Introducció a SQLite

SQLite és una biblioteca de programari que proporciona un sistema de gestió de bases de dades relacional. És lleugera, autònoma i no necessita un servidor separat per funcionar, cosa que la fa ideal per a aplicacions mòbils com les desenvolupades amb Flutter.

Característiques de SQLite

  • Lleugera: No requereix configuració ni administració de servidor.
  • Autònoma: Tot el que necessita està contingut en una única biblioteca.
  • Transaccional: Suporta transaccions ACID (Atomicitat, Consistència, Aïllament, Durabilitat).
  • Integrada: Es pot integrar fàcilment en aplicacions mòbils.

Configuració de SQLite en Flutter

Pas 1: Afegir Dependències

Per utilitzar SQLite en una aplicació Flutter, necessitem afegir les dependències sqflite i path al fitxer pubspec.yaml.

dependencies:
  flutter:
    sdk: flutter
  sqflite: ^2.0.0+3
  path: ^1.8.0

Pas 2: Importar les Biblioteques Necessàries

import 'package:sqflite/sqflite.dart';
import 'package:path/path.dart';

Pas 3: Crear i Obrir la Base de Dades

Future<Database> openDatabase() async {
  final databasePath = await getDatabasesPath();
  final path = join(databasePath, 'my_database.db');

  return openDatabase(
    path,
    onCreate: (db, version) {
      return db.execute(
        "CREATE TABLE items(id INTEGER PRIMARY KEY, name TEXT, value INTEGER)",
      );
    },
    version: 1,
  );
}

Explicació del Codi

  • getDatabasesPath(): Obté el camí del directori on es guardaran les bases de dades.
  • join(): Uneix el camí del directori amb el nom del fitxer de la base de dades.
  • openDatabase(): Obre la base de dades i executa la funció onCreate si la base de dades no existeix.

Operacions CRUD (Crear, Llegir, Actualitzar, Esborrar)

Crear (Insertar)

Future<void> insertItem(Database db, Item item) async {
  await db.insert(
    'items',
    item.toMap(),
    conflictAlgorithm: ConflictAlgorithm.replace,
  );
}

Llegir (Consultar)

Future<List<Item>> items(Database db) async {
  final List<Map<String, dynamic>> maps = await db.query('items');

  return List.generate(maps.length, (i) {
    return Item(
      id: maps[i]['id'],
      name: maps[i]['name'],
      value: maps[i]['value'],
    );
  });
}

Actualitzar

Future<void> updateItem(Database db, Item item) async {
  await db.update(
    'items',
    item.toMap(),
    where: "id = ?",
    whereArgs: [item.id],
  );
}

Esborrar

Future<void> deleteItem(Database db, int id) async {
  await db.delete(
    'items',
    where: "id = ?",
    whereArgs: [id],
  );
}

Explicació del Codi

  • insert(): Insereix un nou registre a la taula.
  • query(): Consulta tots els registres de la taula.
  • update(): Actualitza un registre existent.
  • delete(): Esborra un registre de la taula.

Exemple Complet

class Item {
  final int id;
  final String name;
  final int value;

  Item({required this.id, required this.name, required this.value});

  Map<String, dynamic> toMap() {
    return {
      'id': id,
      'name': name,
      'value': value,
    };
  }
}

void main() async {
  final database = await openDatabase();

  var item = Item(id: 0, name: 'Item 1', value: 100);
  await insertItem(database, item);

  print(await items(database));

  item = Item(id: 0, name: 'Updated Item', value: 200);
  await updateItem(database, item);

  print(await items(database));

  await deleteItem(database, item.id);

  print(await items(database));
}

Exercicis Pràctics

Exercici 1: Crear una Taula Nova

Crea una taula nova anomenada users amb les columnes id, username i password.

Exercici 2: Insertar i Consultar

Insereix un nou usuari a la taula users i consulta tots els usuaris.

Exercici 3: Actualitzar un Usuari

Actualitza el nom d'usuari d'un registre existent a la taula users.

Exercici 4: Esborrar un Usuari

Esborra un usuari de la taula users basant-te en el seu id.

Solucions

Solució Exercici 1

await db.execute(
  "CREATE TABLE users(id INTEGER PRIMARY KEY, username TEXT, password TEXT)",
);

Solució Exercici 2

Future<void> insertUser(Database db, User user) async {
  await db.insert(
    'users',
    user.toMap(),
    conflictAlgorithm: ConflictAlgorithm.replace,
  );
}

Future<List<User>> users(Database db) async {
  final List<Map<String, dynamic>> maps = await db.query('users');

  return List.generate(maps.length, (i) {
    return User(
      id: maps[i]['id'],
      username: maps[i]['username'],
      password: maps[i]['password'],
    );
  });
}

Solució Exercici 3

Future<void> updateUser(Database db, User user) async {
  await db.update(
    'users',
    user.toMap(),
    where: "id = ?",
    whereArgs: [user.id],
  );
}

Solució Exercici 4

Future<void> deleteUser(Database db, int id) async {
  await db.delete(
    'users',
    where: "id = ?",
    whereArgs: [id],
  );
}

Conclusió

En aquesta secció, hem après a configurar i utilitzar SQLite en una aplicació Flutter. Hem cobert les operacions bàsiques de CRUD i hem proporcionat exercicis pràctics per reforçar els conceptes apresos. SQLite és una eina poderosa per gestionar dades localment en aplicacions mòbils, i la seva integració amb Flutter és senzilla i eficient.

Curs de Desenvolupament Flutter

Mòdul 1: Introducció a Flutter

Mòdul 2: Conceptes Bàsics de Programació en Dart

Mòdul 3: Widgets de Flutter

Mòdul 4: Gestió de l'Estat

Mòdul 5: Navegació i Enrutament

Mòdul 6: Xarxes i APIs

Mòdul 7: Persistència i Emmagatzematge

Mòdul 8: Conceptes Avançats de Flutter

Mòdul 9: Proves i Depuració

Mòdul 10: Desplegament i Manteniment

Mòdul 11: Flutter per a Web i Escriptori

© Copyright 2024. Tots els drets reservats