Flutter: ¿Cómo hacer CRUD con PostgreSQL? Parte 2

Hoy voy a compartir algunos temas interesantes como:

  • Cómo construir una API RESTful en un servidor web usando Dart y Aqueduct con integración de Postgresql.
  • Cómo construir la aplicación móvil Flutter y realizar funciones CRUD básicas con la aplicación Aqueduct. estas aqui

De la publicación anterior, he compartido cómo configurar su servidor web para implementar la API RESTful usando Aqueduct con Postgresql. En esta publicación, vamos a comenzar a construir nuestra aplicación de flutter para interactuar con nuestra aplicación web.

Cómo configurar el proyecto Flutter

Cree un nuevo proyecto de Flutter llamado flutter_crud_demo. Si está utilizando Visual Studio Code, puede crear un nuevo proyecto mediante Ver> Paleta de comandos> Agitar nuevo proyecto> Ingresar nombre del proyecto> Seleccionar directorio para guardar su proyecto. Cuando el espacio de trabajo termine de inicializarse, elimine el widget_test.dart y vacíe el contenido del main.dart.

Función de lectura

Futuro constructor

Future Builder nos permite representar una vista de lista tan pronto como obtengamos nuestra lista de datos de forma asincrónica. Future Builder tiene 2 parámetros, uno es el futuro, que es el método futuro que utilizamos para recuperar la lista de datos y el otro es el generador, que es lo que queremos construir con los datos. El uso de Future Builder nos permite mostrar al usuario un CircularProgressIndicator antes de que los datos estén listos y muestra ListView cuando se realiza la recuperación. En nuestro cuerpo de andamio, reemplácelo con el siguiente código.

cuerpo: nuevo contenedor (
  hijo: nuevo FutureBuilder > (
    futuro: getAll (),
    constructor: (contexto, instantánea) {

      if (snapshot.hasData) {
        devolver nuevo ListView.builder (
          itemCount: snapshot.data.length,
          itemBuilder: (contexto, índice) {
            volver nueva columna (
              crossAxisAlignment: CrossAxisAlignment.start,
              hijos:  [
                Texto nuevo (snapshot.data [index] .name,
                  estilo: nuevo TextStyle (fontWeight: FontWeight.bold)),
                nuevo divisor ()
              ]
            );
          }
        );
      } else if (snapshot.hasError) {
        devolver texto nuevo ("$ {snapshot.error}");
      }

      // Por defecto, muestra una rueda de carga
      return new CircularProgressIndicator ();
    },
  ),
),

A continuación, debemos implementar el método getAll () para recuperar la lista de héroes de nuestro servidor web. Nuestro método devuelve una lista de héroes del tipo Futureof. Dentro de la función, llamamos y awaithttp.get (_heroesUrl). Aguardar nos permite esperar una respuesta antes de pasar a la siguiente línea. La función getAll () necesita estar marcada con async para poder usar wait dentro del método. De la respuesta, recuperamos el mensaje del cuerpo y lo convertimos en nuestro

Futuro > getAll () async {
  respuesta final = esperar http.get (_heroesUrl);
  print (respuesta.cuerpo);
  List responseJson = json.decode (response.body.toString ());
  Lista  userList = createHeroesList (responseJson);
  return userList;
}

Necesitamos importar algunas bibliotecas para algunas funciones auxiliares.

importar 'dart: convertir';
importar 'dart: async';
importar 'paquete: http / http.dart' como http;

Vamos a crear una clase llamada Héroe. Esta clase toma un número entero para id y string como nombre.

héroe de clase {
  Héroe ({this.id, this.name});
  id int final;
  Nombre de cadena;
}

Dentro de la clase _MyHomePageState, agregue const estática _heroesUrl para contener nuestra url localhost.

static const _heroesUrl = 'http: // localhost: 8888 / heroes';

Ejecutemos la aplicación Flutter. También recuerde iniciar su aplicación de servidor web con el comando de acueducto.

Podemos obtener una lista de héroes en nuestra aplicación Flutter

Eliminar función

De aquí en adelante, vamos a presentar una enumeración para almacenar el estado de cualquier solicitud http. Cualquier solicitud http debe devolver el tipo HttpRequestStatus.

enumeración HttpRequestStatus {
  NO HECHO
  HECHO,
  ERROR
}

Descartable

Vamos a implementar deslizar para eliminar, que es un patrón muy común que se encuentra en las aplicaciones móviles. Para hacer esto, vamos a intercambiar Columna con Descartable como se muestra a continuación. Luego solicitamos eliminar un héroe por su id en el parámetro onDismissed. El método deleteHero devuelve un futuro que es httpRequestStatus. Si el estado está listo, le pediremos que vuelva a dibujar la pantalla usando setState ().

devolver nuevo ListView.builder (
    itemCount: snapshot.data.length,
    itemBuilder: (contexto, índice) {
      elemento var = snapshot.data [índice];

      volver desestimado (
        clave: Clave (item.id.toString ()),
        onDismissed: (dirección) asíncrono {
          httpRequestStatus = aguarda deleteHero (item.id);
          if (httpRequestStatus == HttpRequestStatus.DONE) {
            setState (() {
              snapshot.data.removeAt (index);
            });
          }
        },
        Fondo: Contenedor (color: Colors.red),
        hijo: ListTile (título: Texto ('$ {item.name}')),
      );
    });

El método deleteHero es el siguiente

Futuro deleteHero (int id) async {
  httpRequestStatus = HttpRequestStatus.NOT_DONE;
  url final = '$ _heroesUrl / $ id';
  respuesta final = esperar http.delete (url, encabezados: _haders);
  if (response.statusCode == 200) {
    print (response.body.toString ());
    httpRequestStatus = HttpRequestStatus.DONE;
  } más {
    httpRequestStatus = HttpRequestStatus.ERROR;
  }

  devolver httpRequestStatus;
}
Desliza para eliminar héroe

Agregar función

Agreguemos un icono de widget debajo de la barra de aplicaciones para permitir al usuario agregar héroe.

appBar: nueva AppBar (
  título: nuevo texto ('Flutter CRUD Demo'),
  acciones:  [
    IconButton (
      icon: Icon (Icons.add),
      onPressed: _addHeroService,
      información sobre herramientas: 'Agregar nuevo héroe',
    )
  ],
),

En _addHeroService, llamamos a _openDialogAddHero para presionar una nueva pantalla para que el usuario ingrese el nombre del héroe. Este método devuelve un nuevo nombre de héroe que luego llamaremos createHero con él y si el nombre del héroe se actualiza con éxito, llamaremos a setState () para volver a dibujar la pantalla.

void _addHeroService () async {
  Nombre de cadena = await _openDialogAddHero ();
  HttpRequestStatus httpRequestStatus = await createHero (nombre);
  if (httpRequestStatus == HttpRequestStatus.DONE) {
    setState (() {
      
    });
  }
}

Agreguemos un encabezado de constante estática para almacenar el tipo de contenido del encabezado http.

static final _headers = {'Content-Type': 'application / json'};

El siguiente es el código para enviar una solicitud para crear un nuevo héroe a la aplicación del servidor web.

Futuro createHero (String name) async {
  httpRequestStatus = HttpRequestStatus.NOT_DONE;
  respuesta final = espera http.post (_heroesUrl,
      encabezados: _heders, cuerpo: json.encode ({'nombre': nombre}));
  if (response.statusCode == 200) {
    print (response.body.toString ());
    httpRequestStatus = HttpRequestStatus.DONE;
  } más {
    httpRequestStatus = HttpRequestStatus.ERROR;
  }

  devolver httpRequestStatus;
}
Podemos agregar un nuevo héroe ahora

Función de actualización

Finalmente, nos queda una última función, que es la capacidad de actualizar el nombre del héroe. Queremos que el usuario toque el héroe existente para actualizar el nombre. Para esto, agregamos un onTap dentro de ListTile que llama al método _updateHeroService, pasando la identificación y el nombre del héroe en ese índice de la lista. Similar al _addHeroService que recupera el nombre del cuadro de diálogo emergente y lo pasa a updateHero. La pantalla se vuelve a dibujar si la actualización de Hero es exitosa.

Futuro _updateHeroService (int id, String name) async {
  Cadena updatedName = await _openDialogUpdateHero (id, nombre);
  HttpRequestStatus httpRequestStatus = await updateHero (id, updatedName);
  if (httpRequestStatus == HttpRequestStatus.DONE) {
    print (httpRequestStatus.toString ());
    setState (() {
      
    });
  }
}

El siguiente es el código para actualizarHero

Actualización futura Hero (int id, String name) async {
  httpRequestStatus = HttpRequestStatus.NOT_DONE;
  url final = '$ _heroesUrl / $ id';
  respuesta final = esperar http.put (url,
      encabezados: _headers, cuerpo: json.encode ({'id': id, 'name': name}));
  if (response.statusCode == 200) {
    print (response.body.toString ());
    httpRequestStatus = HttpRequestStatus.DONE;
  } más {
    httpRequestStatus = HttpRequestStatus.ERROR;
  }
}
Intercambiemos Hawkeye con Thor

Como recapitulación, hemos cubierto cómo construir nuestra aplicación de servidor web implementando la API RESTful y logramos construir una aplicación Flutter para realizar funciones CRUD básicas con PostgreSQL.

Github

https://github.com/tattwei46/flutter_crud_postgresql

Si encuentra este artículo útil y educativo, dele algo para alentarme a escribir más sobre esto en el futuro

El Flutter Pub es una publicación mediana que le ofrece los recursos más recientes y sorprendentes, como artículos, videos, códigos, podcasts, etc. sobre esta gran tecnología para enseñarle cómo crear hermosas aplicaciones con ella. Puede encontrarnos en Facebook, Twitter y Medium u obtener más información sobre nosotros aquí. ¡Nos encantaría conectarnos! Y si usted es un escritor interesado en escribir para nosotros, puede hacerlo a través de estas pautas.