• Publicidad

Cómo obtengo varias filas de mi DB

¿Apenas comienzas con Perl? En este foro podrás encontrar y hacer preguntas básicas de Perl con respuestas aptas a tu nivel.

Cómo obtengo varias filas de mi DB

Notapor neoranger » 2014-11-20 15:13 @675

Hola amigos, ¿cómo están? Quiero saber cómo puedo obtener varias filas desde una consulta MySQL en Perl.

Tengo el siguiente código:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. sub store :Local :Args(0) {
  2.         my ($self, $c) = @_;
  3.  
  4. # connect to the database
  5.         my $dbh = DBI->connect("DBI:mysql:database=datatest", "perltestUser", "password")
  6.         or die $DBI::errstr;
  7.  
  8. # query a la tabla
  9.         my $statement = qq{SELECT * FROM staff};
  10.  
  11.         my $sth = $dbh->prepare($statement)
  12.         or die $dbh->errstr;
  13.  
  14.         $sth->execute()
  15.         or die $sth->errstr;
  16.  
  17.         my ($query_store) = $sth->fetchrow_array;
  18.  
  19.         my $result_query = new Result_query($query_store);
  20.  
  21.         $c->stash{store} = $sth->$query_store;
  22.         $c->forward('View::JSON');
  23. }
  24.  
  25. __PACKAGE__->meta->make_immutable;
  26.  
  27. package Result_query;
  28.  
  29. sub new {
  30.                 my $class = shift;
  31.                 my $self = bless {
  32.                         'staff_id' => shift,
  33.                         'first_name' => shift,
  34.                         'last_name' => shift,
  35.                         'address_id' => shift,
  36.                         'picture' => shift,
  37.                         'email' => shift,
  38.                         'store_id' => shift,
  39.                         'active' => shift,
  40.                         'username' => shift,
  41.                         'password' => shift,
  42.                         'last_update' => shift,
  43.                         }, $class;
  44.                 return $self;
  45. }
  46.  
  47. sub TO_JSON { return { %{ shift() } }; }
  48.  
  49. 1;
  50.  
Coloreado en 0.003 segundos, usando GeSHi 1.0.8.4


Con esto, y puliéndolo por varios errores solo me trae un campo de la consulta que hice, ni siquiera una fila completa, ni por lo menos una fila.

¿Alguno me puede dar una mano para ver qué estoy haciendo mal?

¡Gracias!
Última edición por explorer el 2014-11-20 15:17 @679, editado 1 vez en total
Razón: interrogaciones; admiraciones;
"Ante muchos ojos todos los errores son obvios." Linus Torvalds
Avatar de Usuario
neoranger
Perlero nuevo
Perlero nuevo
 
Mensajes: 34
Registrado: 2014-11-17 08:10 @382

Publicidad

Re: Cómo obtengo varias filas de mi DB

Notapor explorer » 2014-11-20 15:26 @685

fetchrow_array() devuelve una lista de elementos (los elementos de los campos del primer registro del resultado), así que no puedes asignarlo a una variable escalar.

Entonces debes algo así:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1.         my (@query_store) = $sth->fetchrow_array;
  2.  
  3.         my $result_query = Result_query->new(@query_store);
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

Con eso lees el primer registro del resultado de la consulta. Si la consulta devuelve más registros, debes hacer un bucle alrededor de ellos.

Esto está en el manual de DBI:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1.          $sth = $dbh->prepare("SELECT foo, bar FROM table WHERE baz=?");
  2.  
  3.          $sth->execute( $baz );
  4.  
  5.          while ( @row = $sth->fetchrow_array ) {       # leemos una fila cada vez, cada columna es un elemento del array
  6.            print "@row\n";                             # y la pintamos, hasta que no haya más.
  7.          }
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Cómo obtengo varias filas de mi DB

Notapor neoranger » 2014-11-20 15:38 @693

Genial pensé que no se podía hacer eso. Pero ahora tengo un problema de sintaxis, no sé por qué me lo está dando si el código (creo) está bien escrito:

syntax error at /Controller/storemain.pm line 59, near "->stash{store"
Global symbol "$query_store" requires explicit package name at /Controller/storemain.pm line 59.
syntax error at C:\Natanael\Git\perlTest\MvcTest\lib/MvcTest/Controller/storemain.pm line 62, near "}"


Ya verifiqué las llaves y parece que están bien, pero no sé por qué me tira el error con el escalar $query_store, ¿lo tengo que declarar en algún lado? ¿No está ya declarado?

Gracias.
Última edición por explorer el 2014-11-20 15:52 @702, editado 1 vez en total
Razón: se => sé; interrogaciones;
"Ante muchos ojos todos los errores son obvios." Linus Torvalds
Avatar de Usuario
neoranger
Perlero nuevo
Perlero nuevo
 
Mensajes: 34
Registrado: 2014-11-17 08:10 @382

Re: Cómo obtengo varias filas de mi DB

Notapor explorer » 2014-11-20 15:54 @704

El error dice que la variable $query_store se está utilizando pero que no ha sido declarado en ningún lado (no has usado my(), ni our(), ni local()).

Fíjate en mi código... he cambiado $query_store por @query_store, dos veces.

Edito: ya veo el error, está en la línea

$sth->$query_store

¿Qué pretendes hacer en esa línea? Estoy confundido...
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Cómo obtengo varias filas de mi DB

Notapor neoranger » 2014-11-20 16:04 @711

Cambié la función con el ejemplo que me pasaste dejándola así:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. sub store :Local :Args(0) {
  2.         my ($self, $c) = @_;
  3.  
  4. # connect to the database
  5.         my $dbh = DBI->connect("DBI:mysql:database=datatest", "perltestUser", "test")
  6.         or die $DBI::errstr;
  7.  
  8. # query a la tabla
  9.         my $statement = qq{SELECT * FROM staff};
  10.  
  11.         my $sth = $dbh->prepare($statement)
  12.         or die $dbh->errstr;
  13.  
  14.         $sth->execute()
  15.         or die $sth->errstr;
  16.  
  17.         my (@query_store) = $sth->fetchrow_array;
  18.  
  19.         my $result_query = Result_query->new(@query_store);
  20.  
  21.         while (@query_store = $sth->fetchrow_array)
  22.         {
  23.                 $c->stash{store} = $sth->$query_store;
  24.                 $c->forward('View::JSON');
  25.         }
  26. }
  27.  
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4


Lo que quiero hacer con los datos tomados del array (resultado del query) es pasarlo a una vista JSON para que se pueda mostrar en mi servidor. La vista es una tabla común y corriente en blanco, donde se llenará con los datos que estoy sacando de esta consulta.
Última edición por explorer el 2014-11-20 18:55 @830, editado 1 vez en total
Razón: comun => común;
"Ante muchos ojos todos los errores son obvios." Linus Torvalds
Avatar de Usuario
neoranger
Perlero nuevo
Perlero nuevo
 
Mensajes: 34
Registrado: 2014-11-17 08:10 @382

Re: Cómo obtengo varias filas de mi DB

Notapor explorer » 2014-11-20 19:52 @869

Desconozco en qué formato hay que generar la estructura de datos para pasarla a JSON, pero lo que sí veo es el tema de la consulta.

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. sub store :Local :Args(0) {
  2.         my ($self, $c) = @_;
  3.  
  4.         # conectar a la base de datos
  5.         my $dbh = DBI->connect("DBI:mysql:database=datatest", "perltestUser", "test")
  6.             or die $DBI::errstr;
  7.  
  8.         # consuta a la tabla
  9.         my $statement = qq{SELECT * FROM staff};
  10.  
  11.         my $sth = $dbh->prepare($statement)
  12.             or die $dbh->errstr;
  13.  
  14.         $sth->execute()
  15.             or die $sth->errstr;
  16.  
  17.         while (my @query_store = $sth->fetchrow_array)
  18.         {
  19.                 my $result_query = Result_query->new(@query_store);     # creamos un objeto $result_query con el resultado de la consulta
  20.  
  21.                 push @{ $c->stash->{store} }, $query_store;             # almacenamos el objeto en un array dentro de la clave 'store' del hash devuelto por stash
  22.         }
  23.  
  24.         $c->forward('View::JSON');
  25. }
  26.  
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

Como no tengo ni idea de Catalyst, lo más seguro es que la construcción de la estructura de datos esté mal, pero lo importante es que veas cómo se hace el bucle y se va guardando el resultado. A propósito: realmente no necesitarías guardar la consulta en forma de objeto. Con guardar los elementos que se extraen de la base de datos, creo que vale para formar el JSON.

Por ejemplo, en este hilo puedes ver que van recuperando información por líneas, almacenándolas en un array, y luego guardando el array en el stash.

Sería algo así:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. sub store :Local :Args(0) {
  2.         my ($self, $c) = @_;
  3.  
  4.         # conectar a la base de datos
  5.         my $dbh = DBI->connect("DBI:mysql:database=datatest", "perltestUser", "test")
  6.             or die $DBI::errstr;
  7.  
  8.         # consuta a la tabla
  9.         my $statement = qq{SELECT * FROM staff};
  10.  
  11.         my $sth = $dbh->prepare($statement)
  12.             or die $dbh->errstr;
  13.  
  14.         $sth->execute()
  15.             or die $sth->errstr;
  16.  
  17.         my @filas;
  18.  
  19.         my
  20.  
  21.         while (my @query_store = $sth->fetchrow_array)
  22.         {
  23.                 my %hash;
  24.  
  25.                 # inicializamos el %hash con los valores del @query_store
  26.                 @hash{ qw(
  27.                         staff_id
  28.                         first_name
  29.                         last_name
  30.                         address_id
  31.                         picture
  32.                         email
  33.                         store_id
  34.                         active
  35.                         username
  36.                         password
  37.                         last_update
  38.                 ) } = @query_store;
  39.  
  40.                 push @filas, \%hash;            # ya podemos guardar el %hash en el almacén de @filas
  41.         }
  42.  
  43.         $c->stash->{store} = \@filas;           # ponemos todas las @filas en el 'store'
  44.  
  45.         $c->forward('View::JSON');
  46. }
  47.  
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4
Lo dicho: no lo he probado. Pero ya ves que te libras del Result_query.

La línea @hash ... es la forma corta(*) de escribirlo así:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1.                 $hash{staff_id   } = $query_store[ 0];
  2.                 $hash{first_name } = $query_store[ 1];
  3.                 $hash{last_name  } = $query_store[ 2];
  4.                 $hash{address_id } = $query_store[ 3];
  5.                 $hash{picture    } = $query_store[ 4];
  6.                 $hash{email      } = $query_store[ 5];
  7.                 $hash{store_id   } = $query_store[ 6];
  8.                 $hash{active     } = $query_store[ 7];
  9.                 $hash{username   } = $query_store[ 8];
  10.                 $hash{password   } = $query_store[ 9];
  11.                 $hash{last_update} = $query_store[10];
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

(*) se puede escribir de otras maneras.
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Cómo obtengo varias filas de mi DB

Notapor neoranger » 2014-11-21 08:09 @381

Excelente, amigo explorer, esto era justamente lo que estaba buscando: cómo usar un array en vez de tener que crear un objeto para hacer una simple consulta a una tabla.

Gracias de nuevo.

¡Saludos!
"Ante muchos ojos todos los errores son obvios." Linus Torvalds
Avatar de Usuario
neoranger
Perlero nuevo
Perlero nuevo
 
Mensajes: 34
Registrado: 2014-11-17 08:10 @382


Volver a Básico

¿Quién está conectado?

Usuarios navegando por este Foro: No hay usuarios registrados visitando el Foro y 6 invitados