Forum |  HardWare.fr | News | Articles | PC | S'identifier | S'inscrire | Shop Recherche
1514 connectés 

 


 Mot :   Pseudo :  
 
 Page :   1  2  3  4  5  6  7
Auteur Sujet :

[Résolu] Export données en perl

n°2219488
clubber43
Posté le 13-02-2014 à 14:11:43  profilanswer
 

Reprise du message précédent :
a quel moment du pgm, le registre est il lu et la valeur sortie  ? parsqu si je suis la logique du pgm, on envoie la requete, on attent une répone, on décode et on verifie la coherence; puis on recoit le corps du message. Enfin, on lit le mot puis on le lit en entier de 16 bits. Mais au moment de l'exporter sur le $fh, la valeur du champse trouve dans quelle variable, $_ ? du coup, pour lire plusieurs champs, je dois faire une boucle qui vont lire et après une boucle qui va enregistrer dans le hash.
 
@+

mood
Publicité
Posté le 13-02-2014 à 14:11:43  profilanswer
 

n°2219497
gilou
Modérateur
Modzilla
Posté le 13-02-2014 à 14:59:07  profilanswer
 

Je te réponds dans une heure.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2219499
clubber43
Posté le 13-02-2014 à 14:59:51  profilanswer
 

ok, merci beaucoup,  
Je fais un peu de code et je le post.
 
merci bien

n°2219511
clubber43
Posté le 13-02-2014 à 15:25:17  profilanswer
 

#!/usr/bin/perl
 
use strict;
use warnings;
use Socket;
 
# Paramètres ModBus/TCP
my $MODBUS_PORT                                    = 502;
 
# Codes des fonctions lecture, ecriture, ...
my $READ_COILS                                    = 0x01;
my $READ_DISCRETE_INPUTS                          = 0x02;
my $READ_HOLDING_REGISTERS                    = 0x03;
my $READ_INPUT_REGISTERS                         = 0x04;
my $WRITE_SINGLE_COIL                             = 0x05;
my $WRITE_SINGLE_REGISTER                    = 0x06;
 
# Codes des exceptions erreurs, ...
my $EXP_ILLEGAL_FUNCTION                          = 0x01;
my $EXP_DATA_ADDRESS                              = 0x02;
my $EXP_DATA_VALUE                                = 0x03;
my $EXP_SLAVE_DEVICE_FAILURE                      = 0x04;
my $EXP_ACKNOWLEDGE                               = 0x05;
my $EXP_SLAVE_DEVICE_BUSY                         = 0x06;
my $EXP_MEMORY_PARITY_ERROR                       = 0x08;
my $EXP_GATEWAY_PATH_UNAVAILABLE                 = 0x0A;
my $EXP_GATEWAY_TARGET_DEVICE_FAILED_TO_RESPOND = 0x0B;
 
# Valeurs par défaut  
my $opt_server                                  = 'localhost';
my $opt_server_port                             = $MODBUS_PORT;  #502
my $opt_timeout                                 = 1;   # temps max de 1 s  
my $opt_unit_id                                 = 1;
my $opt_mb_fc                                   = $READ_HOLDING_REGISTERS;
my $opt_mb_ad                                   = 267; # adresse du mot1 à lire et exporter
my $opt_mb_ad2                                  = 305; # adresse du mot2 à lire et exporter
my $opt_mb_nb                                   = 1;
my $opt_bit_value                               = 0;
my $opt_word_value                              = 0;
 
 
 
 
$opt_server = '192.168.1.253';      # @ IP du serveur TCP
my $server_ip = inet_aton($opt_server);    # on donne l'@ IP à la variable
unless ($server_ip) {  
  print STDERR 'unable to resolve "'.$opt_server.'"'."\n"; # et la,  
  exit 1;  
}  
 
my $status = query_info();  
until ($status) {  
 sleep(1);  # toutes les 1s, a adapter à ses besoins  
 $status = query_info();  
}  
 
# boucle infinie, a stopper avec un kill      
# tourne sas cesse jusqu'au ctrl+C
 
sub query_info {      
 
  # Gestion du dialogue reseau
  # Ouverture de la session TCP
 
  socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
  unless (connect(SERVER, sockaddr_in($MODBUS_PORT, $server_ip))) {
    print STDERR 'connexion au serveur "'.$server_ip.':'.$MODBUS_PORT.'" impossible'."\n";
    return 2;
  }
   
  # Création de la requête  
  my $tx_hd_tr_id   = int(rand 65535);
  my $tx_hd_length  = 6;
  my $tx_hd_pr_id   = 0;
  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);
 
  # Emission de la requête
  send(SERVER, $tx_buffer, 0);
   
  # Attente d'une réponse
  unless (can_read('SERVER', $opt_timeout)) {
    close SERVER;
    print STDERR 'receive timeout'."\n";
    return 1;
  }
 
  # Réception de l'entête
  my ($rx_frame, $rx_buffer);
  recv(SERVER, $rx_buffer, 7, 0);
  $rx_frame = $rx_buffer;
 
  # Décodage de l'entête
  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;
 
  # Vérifie la cohérence de l'entête
  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&
      ($rx_hd_pr_id == 0) &&
      ($rx_hd_length < 256) &&
      ($rx_hd_unit_id == 1)) {
    close SERVER;
    print STDERR 'error in receive frame'."\n";
    return 1;
  }
 
  # Réception du corps du message
  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);
  $rx_frame .= $rx_buffer;
  close SERVER;
 
  # Décodage du corps du message
  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;
 
  # Vérification du statut d'exception
  if ($rx_bd_fc > 0x80) {
 
    # Affichage du code exception
    my ($rx_except_code) = unpack "C", $rx_body;
    print 'exception (code '.$rx_except_code.')'."\n";
  }  
 
else {
 
    ## Lecture de mot
    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;
 
    # Lecture d'entier de 16 bits
    my @rx_disp_data = unpack 'n*', $rx_read_word_data;
    disp_data(@rx_disp_data);
  }
  return 0;
}
 
 
 
 
 
 
# Attend $timeout secondes que le socket mette à disposition des données
sub can_read {
my $infos{conso_P}=0 ;
  my ($sock_handle, $timeout) ={conso_P}= ;
  my $hdl_select = "";
  vec($hdl_select, fileno($sock_handle), 1) = 1;
  return (select($hdl_select, undef, undef, $timeout) == 1);
}
 
 # Affichage des valeurs recues  
 
sub disp_data {  
my $infos ;
foreach (@_)  
{
print ("$infos{{conso_P}=} = {conso_P} " );
}
}
 par exemple pour un hash ?

n°2219549
gilou
Modérateur
Modzilla
Posté le 13-02-2014 à 16:38:40  profilanswer
 

C'est ce bout la qui correspond a une requête avec lecture de la réponse.

# Création de la requête    
  my $tx_hd_tr_id   = int(rand 65535);  
  my $tx_hd_length  = 6;  
  my $tx_hd_pr_id   = 0;  
  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);  
   
  # Emission de la requête  
  send(SERVER, $tx_buffer, 0);  
   
  # Attente d'une réponse  
  unless (can_read('SERVER', $opt_timeout)) {  
    close SERVER;  
    print STDERR 'receive timeout'."\n";  
    return 1;  
  }  
   
  # Réception de l'entête  
  my ($rx_frame, $rx_buffer);  
  recv(SERVER, $rx_buffer, 7, 0);  
  $rx_frame = $rx_buffer;  
   
  # Décodage de l'entête  
  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;  
   
  # Vérifie la cohérence de l'entête  
  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&  
      ($rx_hd_pr_id == 0) &&  
      ($rx_hd_length < 256) &&  
      ($rx_hd_unit_id == 1)) {  
    close SERVER;  
    print STDERR 'error in receive frame'."\n";  
    return 1;  
  }  
   
  # Réception du corps du message  
  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);  
  $rx_frame .= $rx_buffer;  
  close SERVER;  
   
  # Décodage du corps du message  
  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;  
   
  # Vérification du statut d'exception  
  if ($rx_bd_fc > 0x80) {  
 
    # Affichage du code exception  
    my ($rx_except_code) = unpack "C", $rx_body;  
    print 'exception (code '.$rx_except_code.')'."\n";  
  }  
 
else {  
 
    ## Lecture de mot  
    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;  
 
    # Lecture d'entier de 16 bits  
    my @rx_disp_data = unpack 'n*', $rx_read_word_data;


 
On va donc le remplacer par une boucle:
avec une liste des adresses a interroger sur laquelle on boucle
my @adresses = qw(267 305);
et un hash pour les réponses
my %result;
 

Code :
  1. my @adresses = qw(267 305);
  2. my %result;
  3.  
  4. foreach (@adresses) {   ####
  5.   $opt_mb_ad = $_;      ####
  6. # Création de la requête  
  7.  my $tx_hd_tr_id   = int(rand 65535);
  8.  my $tx_hd_length  = 6;
  9.  my $tx_hd_pr_id   = 0;
  10.  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);
  11.  
  12.  # Emission de la requête
  13.  send(SERVER, $tx_buffer, 0);
  14.  
  15.  # Attente d'une réponse
  16.  unless (can_read('SERVER', $opt_timeout)) {
  17.    close SERVER;
  18.    print STDERR 'receive timeout'."\n";
  19.    return 1;
  20.  }
  21.  
  22.  # Réception de l'entête
  23.  my ($rx_frame, $rx_buffer);
  24.  recv(SERVER, $rx_buffer, 7, 0);
  25.  $rx_frame = $rx_buffer;
  26.  
  27.  # Décodage de l'entête
  28.  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;
  29.  
  30.  # Vérifie la cohérence de l'entête
  31.  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&
  32.      ($rx_hd_pr_id == 0) &&
  33.      ($rx_hd_length < 256) &&
  34.      ($rx_hd_unit_id == 1)) {
  35.    close SERVER;
  36.    print STDERR 'error in receive frame'."\n";
  37.    return 1;
  38.  }
  39.  
  40.  # Réception du corps du message
  41.  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);
  42.  $rx_frame .= $rx_buffer;
  43.  close SERVER;
  44.  
  45.  # Décodage du corps du message
  46.  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;
  47.  
  48.  # Vérification du statut d'exception
  49.  if ($rx_bd_fc > 0x80) {
  50.  
  51.    # Affichage du code exception
  52.    my ($rx_except_code) = unpack "C", $rx_body;
  53.    print 'exception (code '.$rx_except_code.')'."\n";
  54.  }  
  55.  
  56. else {
  57.  
  58.    ## Lecture de mot
  59.    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;
  60.  
  61.    # Lecture d'entier de 16 bits
  62.    # un seul registre a lire d'ou le 'n'
  63.    $result{$opt_mb_ad} = unpack 'n', $rx_read_word_data; ####
  64.    }
  65. } # fin de la boucle foreach  ####
  66. #impression en console
  67. foreach (sort {$a <=> $b} (keys %result)) {
  68.    print "<$_> : $result{$_};"
  69. }
  70. print "\n";


Routine d'impression à adapter pour une écriture fichier, le format que tu veux, etc.
Comme tu vois, pour la boucle de requêtes, il y a très peu de modifications (visibles avec le ####): 4 lignes seulement.
A+,


Message édité par gilou le 13-02-2014 à 16:44:34

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2219613
clubber43
Posté le 14-02-2014 à 08:46:41  profilanswer
 

C'est sympa pour le coup demain.
En fait, contrairement au C, on peut passer plusieurs éléments en parametres et grâce à la boucle foreach (@adresses) {   ####;
on peut faire pas mal de choses ^^
 
Le hash, permet en fait de rapporter plusieurs valeurs dans une seule variable si j'ai bien compris. C'est quand même pas mal comparé au C ou C++ :)

n°2219618
clubber43
Posté le 14-02-2014 à 09:30:23  profilanswer
 

j'ai refais un bout de pgm pour l'export, mais j'ai comme erreurs :  
 send () on closed socket server at c:/ line 84  
Use of uninitialized value in vec at c:/ line 149
 
 

Code :
  1. #!/usr/bin/perl
  2.  
  3.  use strict;
  4.  use warnings;
  5.  use Socket;
  6.  
  7. # Paramètres ModBus/TCP
  8.  my $MODBUS_PORT                                 = 502;
  9.  
  10. # Codes des fonctions lecture, ecriture, ...
  11.  my $READ_COILS                                  = 0x01;
  12.  my $READ_DISCRETE_INPUTS                        = 0x02;
  13.  my $READ_HOLDING_REGISTERS                      = 0x03;
  14.  my $READ_INPUT_REGISTERS                        = 0x04;
  15.  my $WRITE_SINGLE_COIL                           = 0x05;
  16.  my $WRITE_SINGLE_REGISTER                       = 0x06;
  17.  
  18. # Codes des exceptions erreurs, ...
  19.  my $EXP_ILLEGAL_FUNCTION                        = 0x01;
  20.  my $EXP_DATA_ADDRESS                            = 0x02;
  21.  my $EXP_DATA_VALUE                              = 0x03;
  22.  my $EXP_SLAVE_DEVICE_FAILURE                    = 0x04;
  23.  my $EXP_ACKNOWLEDGE                             = 0x05;
  24.  my $EXP_SLAVE_DEVICE_BUSY                       = 0x06;
  25.  my $EXP_MEMORY_PARITY_ERROR                     = 0x08;
  26.  my $EXP_GATEWAY_PATH_UNAVAILABLE                = 0x0A;
  27.  my $EXP_GATEWAY_TARGET_DEVICE_FAILED_TO_RESPOND = 0x0B;
  28.  
  29. # Valeurs par défaut
  30.  my $opt_server                                  = 'localhost';
  31.  my $opt_server_port                             = $MODBUS_PORT;        #502
  32.  my $opt_timeout                                 = 1;            # temps max de 1 s        
  33.  my $opt_unit_id                                 = 1;
  34.  my $opt_mb_fc                                   = $READ_HOLDING_REGISTERS;
  35.  my $opt_mb_ad                                   = 267; # adresse du mot1 à lire et exporter
  36.  my $opt_mb_ad2                                  = 305; # adresse du mot2 à lire et exporter
  37.  my $opt_mb_nb                                   = 1;
  38.  my $opt_bit_value                               = 0;
  39.  my $opt_word_value                              = 0;
  40.  
  41.  
  42.  
  43.  
  44.  $opt_server = '192.168.1.253';                      # @ IP du serveur TCP
  45.  my $server_ip = inet_aton($opt_server);                  # on donne l'@ IP à la variable
  46.  unless ($server_ip) {  
  47.  print STDERR 'unable to resolve "'.$opt_server.'"'."\n"; # et la,  
  48.  exit 1;  
  49.  }  
  50.  
  51.  my $status = query_info();
  52.  until ($status) {
  53.  sleep(1);  # toutes les 1s, a adapter à ses besoins
  54.  $status = query_info();
  55.  }
  56. # boucle infinie, a stopper avec un kill                 # tourne sas cesse jusqu'au ctrl+C
  57.  
  58.  
  59.  
  60.  
  61. sub query_info {                    
  62.  
  63. # Gestion du dialogue reseau
  64. # Ouverture de la session TCP
  65.  
  66.  socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
  67.  unless (connect(SERVER, sockaddr_in($MODBUS_PORT, $server_ip))) {
  68.    print STDERR 'connexion au serveur "'.$server_ip.':'.$MODBUS_PORT.'" impossible'."\n";
  69.    return 2;
  70.  }
  71.  
  72.  my @adresses = qw(267 305);
  73.  my %result;
  74.  
  75.  foreach (@adresses) {   ####
  76.  $opt_mb_ad = $_;      ####
  77. # Création de la requête  
  78.  my $tx_hd_tr_id   = int(rand 65535);
  79.  my $tx_hd_length  = 6;
  80.  my $tx_hd_pr_id   = 0;
  81.  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);
  82.  
  83. # Emission de la requête
  84.  send(SERVER, $tx_buffer, 0);
  85.  
  86. # Attente d'une réponse
  87.  unless (can_read('SERVER', $opt_timeout)) {
  88.    close SERVER;
  89.    print STDERR 'receive timeout'."\n";
  90.    return 1;
  91.  }
  92.  
  93. # Réception de l'entête
  94.  my ($rx_frame, $rx_buffer);
  95.  recv(SERVER, $rx_buffer, 7, 0);
  96.  $rx_frame = $rx_buffer;
  97.  
  98. # Décodage de l'entête
  99.  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;
  100.  
  101. # Vérifie la cohérence de l'entête
  102.  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&
  103.      ($rx_hd_pr_id == 0) &&
  104.      ($rx_hd_length < 256) &&
  105.      ($rx_hd_unit_id == 1)) {
  106.    close SERVER;
  107.    print STDERR 'error in receive frame'."\n";
  108.    return 1;
  109.  }
  110.  
  111. # Réception du corps du message
  112.  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);
  113.  $rx_frame .= $rx_buffer;
  114.  close SERVER;
  115.  
  116. # Décodage du corps du message
  117.  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;
  118.  
  119. # Vérification du statut d'exception
  120.  if ($rx_bd_fc > 0x80) {
  121.  
  122. # Affichage du code exception
  123.    my ($rx_except_code) = unpack "C", $rx_body;
  124.    print 'exception (code '.$rx_except_code.')'."\n";
  125.  }  
  126.  
  127.  else {
  128.  
  129. ## Lecture de mot
  130.    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;
  131.  
  132. # Lecture d'entier de 16 bits
  133. # un seul registre a lire d'ou le 'n'
  134.    $result{$opt_mb_ad} = unpack 'n', $rx_read_word_data; ####
  135.    }
  136.    }
  137. # fin de la boucle foreach  ####
  138. # impression en console
  139.  
  140.  foreach (sort {$a <=> $b} (keys %result)) {
  141.  print "<$_> : $result{$_};"
  142. }
  143. print "\n";
  144.  
  145. ########################" attente $timeout###################################
  146.  sub can_read{
  147. my ($sock_handle, $timeout) = @_;
  148. my $hdl_select="";
  149. vec($hdl_select, fileno($sock_handle),1)=1;
  150. return (select($hdl_select, undef, undef, $timeout)==1);
  151. }
  152. ############################################################################
  153.  
  154.  
  155. # Affichage des valeurs recues
  156.  
  157. sub disp_data {
  158.  
  159. open(my $fh, ">>", 'C:/julien/test.csv' ) || die ('Impossible de créer le fichier "c:/julien/test.csv"' );
  160.  
  161. foreach (@_)
  162. {
  163.  printf( $fh "%05d;", $_);
  164. }
  165. printf ($fh "\n" );
  166.  
  167. close ($fh);
  168.  
  169.  
  170. }
  171.  
  172. }


 
 
Je ne vois pas où se situe l'erreur.
J'ai refais un bout pour l'export en csv ou txt, et aussi déclarer la sub can_read qui manquait. Mais c'est peut-etre faux ^^
 
@ tento


Message édité par gilou le 14-02-2014 à 12:08:35
n°2219638
gilou
Modérateur
Modzilla
Posté le 14-02-2014 à 12:13:47  profilanswer
 

L'erreur est a la ligne 114:
  close SERVER;  
il faut la mettre après la fin de la nouvelle boucle foreach.  
 
Pour le can_read, c'est normal, je t'ai donné un bout de code modifié hier, c'est à toi de l'insérer dans l'ancien code.
 
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2219640
clubber43
Posté le 14-02-2014 à 13:40:18  profilanswer
 

#!/usr/bin/perl
 
  use strict;
  use warnings;
  use Socket;
 
# Paramètres ModBus/TCP
  my $MODBUS_PORT                                 = 502;
 
# Codes des fonctions lecture, ecriture, ...
  my $READ_COILS                                  = 0x01;
  my $READ_DISCRETE_INPUTS                        = 0x02;
  my $READ_HOLDING_REGISTERS                      = 0x03;
  my $READ_INPUT_REGISTERS                        = 0x04;
  my $WRITE_SINGLE_COIL                           = 0x05;
  my $WRITE_SINGLE_REGISTER                       = 0x06;
 
# Codes des exceptions erreurs, ...
  my $EXP_ILLEGAL_FUNCTION                        = 0x01;
  my $EXP_DATA_ADDRESS                            = 0x02;
  my $EXP_DATA_VALUE                              = 0x03;
  my $EXP_SLAVE_DEVICE_FAILURE                    = 0x04;
  my $EXP_ACKNOWLEDGE                             = 0x05;
  my $EXP_SLAVE_DEVICE_BUSY                       = 0x06;
  my $EXP_MEMORY_PARITY_ERROR                     = 0x08;
  my $EXP_GATEWAY_PATH_UNAVAILABLE                = 0x0A;
  my $EXP_GATEWAY_TARGET_DEVICE_FAILED_TO_RESPOND = 0x0B;
 
# Valeurs par défaut  
  my $opt_server                                  = 'localhost';
  my $opt_server_port                             = $MODBUS_PORT;  #502
  my $opt_timeout                                 = 1;   # temps max de 1 s  
  my $opt_unit_id                                 = 1;
  my $opt_mb_fc                                   = $READ_HOLDING_REGISTERS;
  my $opt_mb_ad                                   = 267; # adresse du mot1 à lire et exporter
  my $opt_mb_ad2                                  = 305; # adresse du mot2 à lire et exporter
  my $opt_mb_nb                                   = 1;
  my $opt_bit_value                               = 0;
  my $opt_word_value                              = 0;
 
 
 
 
  $opt_server = '192.168.1.253';       # @ IP du serveur TCP
  my $server_ip = inet_aton($opt_server);      # on donne l'@ IP à la variable
  unless ($server_ip) {  
  print STDERR 'unable to resolve "'.$opt_server.'"'."\n"; # et la,  
  exit 1;  
  }  
 
  my $status = query_info();  
  until ($status) {  
  sleep(1);  # toutes les 1s, a adapter à ses besoins  
  $status = query_info();  
  }  
# boucle infinie, a stopper avec un kill     # tourne sas cesse jusqu'au ctrl+C
   
 
 
 
sub query_info {      
 
# Gestion du dialogue reseau
# Ouverture de la session TCP
 
  socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
  unless (connect(SERVER, sockaddr_in($MODBUS_PORT, $server_ip))) {
    print STDERR 'connexion au serveur "'.$server_ip.':'.$MODBUS_PORT.'" impossible'."\n";
    return 2;
  }
   
  my @adresses = qw(267 305);
  my %result;
 
  foreach (@adresses) {   ####
  $opt_mb_ad = $_;      ####
# Création de la requête    
  my $tx_hd_tr_id   = int(rand 65535);  
  my $tx_hd_length  = 6;  
  my $tx_hd_pr_id   = 0;  
  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);  
   
# Emission de la requête  
  send(SERVER, $tx_buffer, 0);  
   
# Attente d'une réponse  
  unless (can_read('SERVER', $opt_timeout)) {  
    close SERVER;  
    print STDERR 'receive timeout'."\n";  
    return 1;  
  }  
   
# Réception de l'entête  
  my ($rx_frame, $rx_buffer);  
  recv(SERVER, $rx_buffer, 7, 0);  
  $rx_frame = $rx_buffer;  
   
# Décodage de l'entête  
  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;  
   
# Vérifie la cohérence de l'entête  
  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&  
      ($rx_hd_pr_id == 0) &&  
      ($rx_hd_length < 256) &&  
      ($rx_hd_unit_id == 1)) {  
    close SERVER;  
    print STDERR 'error in receive frame'."\n";  
    return 1;  
  }  
   
# Réception du corps du message  
  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);  
  $rx_frame .= $rx_buffer;  
   
   
# Décodage du corps du message  
  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;  
   
# Vérification du statut d'exception  
  if ($rx_bd_fc > 0x80) {  
 
# Affichage du code exception  
    my ($rx_except_code) = unpack "C", $rx_body;  
    print 'exception (code '.$rx_except_code.')'."\n";  
  }  
 
  else {  
 
## Lecture de mot  
    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;  
 
# Lecture d'entier de 16 bits  
# un seul registre a lire d'ou le 'n'
    $result{$opt_mb_ad} = unpack 'n', $rx_read_word_data; ####
    }
    }
close SERVER;  
 # fin de la boucle foreach  ####
 # impression en console
 
  foreach (sort {$a <=> $b} (keys %result)) {
  print "<$_> : $result{$_};"
}
 print "\n";
 
########################" attente $timeout###################################
  sub can_read{
 my ($sock_handle, $timeout) = @_;
 my $hdl_select="";
 vec($hdl_select, fileno($sock_handle),1)=1;
 return (select($hdl_select, undef, undef, $timeout)==1);
}
############################################################################
 
 
# Affichage des valeurs recues  
 
 sub disp_data {  
 
 open(my $fh, ">>", 'C:/test.csv' ) || die ('Impossible de créer le fichier "c:/test.csv"' );  
 
 foreach (@_)  
 {
  printf( $fh "%05d;", $_);
 }
 printf ($fh "\n" );
 
close ($fh);  
 
 
}
 
}
 J'ai fais la modification sur les boucles sur-read et sur la boucle d'écriture dans le fichier, mais pas d'export en csv. Le script se lance sans probleme de compilation. Il y a surement un souci sur la ligne sub_read à mon avis ? non ?  
 
@+

n°2219644
gilou
Modérateur
Modzilla
Posté le 14-02-2014 à 14:09:35  profilanswer
 

Ca n'a aucune raison de marcher, puisque c'est faux!
 
La dernière accolade fermante, elle doit être après le print "\n"; afin de clore la procédure query info avant qu'on définisse les autres.
 
et rajouter disp_data alors qu'on ne l'appelle pas dans le code, c'est normal que ça ne fasse rien.
 
La, le code qui va adfficher les infos en console est ici:
  foreach (sort {$a <=> $b} (keys %result)) {  
  print "<$_> : $result{$_};"  
}  
 print "\n";
 
vous pouvez remplacer ça par un  
disp_data(%result);
 
et écrire une procédure disp_data qui fasse le travail, pour un hash et non un array.
 
A+,


Message édité par gilou le 14-02-2014 à 14:11:08

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
mood
Publicité
Posté le 14-02-2014 à 14:09:35  profilanswer
 

n°2219645
clubber43
Posté le 14-02-2014 à 14:15:39  profilanswer
 

Ok, je refais le bout de programme et si jamais sa marche (ou pas) je reviens sur le post.
 
Sinon, un bon weekend et une bonne fin d'après-midi
 
Julien

n°2219652
clubber43
Posté le 14-02-2014 à 14:48:51  profilanswer
 

Et voila après modif :
 
#!/usr/bin/perl
 
  use strict;
  use warnings;
  use Socket;
 
# Paramètres ModBus/TCP
  my $MODBUS_PORT                                 = 502;
 
# Codes des fonctions lecture, ecriture, ...
  my $READ_COILS                                  = 0x01;
  my $READ_DISCRETE_INPUTS                        = 0x02;
  my $READ_HOLDING_REGISTERS                      = 0x03;
  my $READ_INPUT_REGISTERS                        = 0x04;
  my $WRITE_SINGLE_COIL                           = 0x05;
  my $WRITE_SINGLE_REGISTER                       = 0x06;
 
# Codes des exceptions erreurs, ...
  my $EXP_ILLEGAL_FUNCTION                        = 0x01;
  my $EXP_DATA_ADDRESS                            = 0x02;
  my $EXP_DATA_VALUE                              = 0x03;
  my $EXP_SLAVE_DEVICE_FAILURE                    = 0x04;
  my $EXP_ACKNOWLEDGE                             = 0x05;
  my $EXP_SLAVE_DEVICE_BUSY                       = 0x06;
  my $EXP_MEMORY_PARITY_ERROR                     = 0x08;
  my $EXP_GATEWAY_PATH_UNAVAILABLE                = 0x0A;
  my $EXP_GATEWAY_TARGET_DEVICE_FAILED_TO_RESPOND = 0x0B;
 
# Valeurs par défaut  
  my $opt_server                                  = 'localhost';
  my $opt_server_port                             = $MODBUS_PORT;  #502
  my $opt_timeout                                 = 1;   # temps max de 1 s  
  my $opt_unit_id                                 = 1;
  my $opt_mb_fc                                   = $READ_HOLDING_REGISTERS;
  my $opt_mb_ad                                   = 267; # adresse du mot1 à lire et exporter
  my $opt_mb_ad2                                  = 305; # adresse du mot2 à lire et exporter
  my $opt_mb_nb                                   = 1;
  my $opt_bit_value                               = 0;
  my $opt_word_value                              = 0;
 
 
 
 
  $opt_server = '192.168.1.253';       # @ IP du serveur TCP
  my $server_ip = inet_aton($opt_server);      # on donne l'@ IP à la variable
  unless ($server_ip) {  
  print STDERR 'unable to resolve "'.$opt_server.'"'."\n"; # et la,  
  exit 1;  
  }  
 
  my $status = query_info();  
  until ($status) {  
  sleep(1);  # toutes les 1s, a adapter à ses besoins  
  $status = query_info();  
  }  
# boucle infinie, a stopper avec un kill     # tourne sas cesse jusqu'au ctrl+C
   
 
 
 
sub query_info {      
 
# Gestion du dialogue reseau
# Ouverture de la session TCP
 
  socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
  unless (connect(SERVER, sockaddr_in($MODBUS_PORT, $server_ip))) {
    print STDERR 'connexion au serveur "'.$server_ip.':'.$MODBUS_PORT.'" impossible'."\n";
    return 2;
  }
   
  my @adresses = qw(267 375 15 64);
  my %result;
 
  foreach (@adresses) {   ####
  $opt_mb_ad = $_;      ####
# Création de la requête    
  my $tx_hd_tr_id   = int(rand 65535);  
  my $tx_hd_length  = 6;  
  my $tx_hd_pr_id   = 0;  
  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);  
   
# Emission de la requête  
  send(SERVER, $tx_buffer, 0);  
   
# Attente d'une réponse  
  unless (can_read('SERVER', $opt_timeout)) {  
    close SERVER;  
    print STDERR 'receive timeout'."\n";  
    return 1;  
  }  
   
# Réception de l'entête  
  my ($rx_frame, $rx_buffer);  
  recv(SERVER, $rx_buffer, 7, 0);  
  $rx_frame = $rx_buffer;  
   
# Décodage de l'entête  
  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;  
   
# Vérifie la cohérence de l'entête  
  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&  
      ($rx_hd_pr_id == 0) &&  
      ($rx_hd_length < 256) &&  
      ($rx_hd_unit_id == 1)) {  
    close SERVER;  
    print STDERR 'error in receive frame'."\n";  
    return 1;  
  }  
   
# Réception du corps du message  
  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);  
  $rx_frame .= $rx_buffer;  
   
   
# Décodage du corps du message  
  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;  
   
# Vérification du statut d'exception  
  if ($rx_bd_fc > 0x80) {  
 
# Affichage du code exception  
    my ($rx_except_code) = unpack "C", $rx_body;  
    print 'exception (code '.$rx_except_code.')'."\n";  
  }  
 
  else {  
 
## Lecture de mot  
    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;  
 
# Lecture d'entier de 16 bits  
# un seul registre a lire d'ou le 'n'
    $result{$opt_mb_ad} = unpack 'n', $rx_read_word_data; ####
    }
    }
close SERVER;  
 # fin de la boucle foreach  ####
 # impression en console
 
 foreach (sort {$a <=> $b} (keys %result)) {  
  print "<$_> : $result{$_};"  
}  
 print "\n";  
 
########################" attente $timeout###################################
  sub can_read{
 my ($sock_handle, $timeout) = @_;
 my $hdl_select="";
 vec($hdl_select, fileno($sock_handle),1)=1;
 return (select($hdl_select, undef, undef, $timeout)==1);
}
############################################################################
 
 
# Affichage des valeurs recues  
 
 sub disp_data {  
 
 open(my $fh, ">>", 'C:/test.csv' ) || die ('Impossible de créer le fichier "c:/test.csv"' );  
 {
  printf( $fh "$result{_$}"{$_} for (keys %result));
 }
 
close ($fh); }
}
 
Il me dit :  
 
variable %result will not stay shared
Syntax error near "$result{$_}"
 
Je suis d'un ennui avec toutes mes questions ^^
 
merci

n°2219717
gilou
Modérateur
Modzilla
Posté le 14-02-2014 à 17:59:44  profilanswer
 

déjà
 
sub disp_data {  
 
 open(my $fh, ">>", 'C:/test.csv' ) || die ('Impossible de créer le fichier "c:/test.csv"' );  
 {
  printf( $fh "$result{_$}" {$_} for (keys %result));  
 }  
   
close ($fh); }
}  
 
Faudrait peut être arrêter d’écrire n'importe quoi en priant pour que ça marche et ouvrir un peu un manuel de perl.
 

Code :
  1. sub disp_data {  
  2.  my %result = @_;
  3.  
  4.  open(my $fh, ">>", 'C:/test.csv' ) || die ('Impossible d\'ouvrir le fichier "c:/test.csv"' );  
  5.  print $fh "$_;$result{$_};" foreach (keys %result));
  6.  print $fh, "\n";
  7.  close ($fh);
  8. }


 
ça devrait le faire, avec un appel disp_data(%result); a mettre la ou il faut.
 
A+,


Message édité par gilou le 14-02-2014 à 18:02:04

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2219879
clubber43
Posté le 17-02-2014 à 09:57:50  profilanswer
 

OK,  
 
c'est pas que j'écrit n'importe quoi, mais c'est assez dur de progresser sans faire de faute. Là, je me donne encore un peu de temps pour y arriver ^^ je comprends le code, et après, j'essaie de faire un autre pgm !!
 
merci gilou

n°2221286
clubber43
Posté le 03-03-2014 à 10:49:53  profilanswer
 

Après plusieur essais, j'ai essayé de voir pourquoi cela ne marchais pas, et j'ai aussi une erreur,  
Lors du script :  
 - Syntax error line163 near $results{$_} " for "  
 - Variable %results will not stay shared at line 163
 
Et voilà le code.
 
#!/usr/bin/perl
 
  use strict;
  use warnings;
  use Socket;
 
# Paramètres ModBus/TCP
  my $MODBUS_PORT                                 = 502;
 
# Codes des fonctions lecture, ecriture, ...
  my $READ_COILS                                  = 0x01;
  my $READ_DISCRETE_INPUTS                        = 0x02;
  my $READ_HOLDING_REGISTERS                      = 0x03;
  my $READ_INPUT_REGISTERS                        = 0x04;
  my $WRITE_SINGLE_COIL                           = 0x05;
  my $WRITE_SINGLE_REGISTER                       = 0x06;
 
# Codes des exceptions erreurs, ...
  my $EXP_ILLEGAL_FUNCTION                        = 0x01;
  my $EXP_DATA_ADDRESS                            = 0x02;
  my $EXP_DATA_VALUE                              = 0x03;
  my $EXP_SLAVE_DEVICE_FAILURE                    = 0x04;
  my $EXP_ACKNOWLEDGE                             = 0x05;
  my $EXP_SLAVE_DEVICE_BUSY                       = 0x06;
  my $EXP_MEMORY_PARITY_ERROR                     = 0x08;
  my $EXP_GATEWAY_PATH_UNAVAILABLE                = 0x0A;
  my $EXP_GATEWAY_TARGET_DEVICE_FAILED_TO_RESPOND = 0x0B;
 
# Valeurs par défaut  
  my $opt_server                                  = 'localhost';
  my $opt_server_port                             = $MODBUS_PORT;  #502
  my $opt_timeout                                 = 1;   # temps max de 1 s  
  my $opt_unit_id                                 = 1;
  my $opt_mb_fc                                   = $READ_HOLDING_REGISTERS;
  my $opt_mb_ad                                   = 267; # adresse du mot1 à lire et exporter
  my $opt_mb_ad2                                  = 305; # adresse du mot2 à lire et exporter
  my $opt_mb_nb                                   = 1;
  my $opt_bit_value                               = 0;
  my $opt_word_value                              = 0;
 
 
 
 
  $opt_server = '192.168.1.253';       # @ IP du serveur TCP
  my $server_ip = inet_aton($opt_server);      # on donne l'@ IP à la variable
  unless ($server_ip) {  
  print STDERR 'unable to resolve "'.$opt_server.'"'."\n"; # et la,  
  exit 1;  
  }  
 
  my $status = query_info();  
  until ($status) {  
  sleep(1);  # toutes les 1s, a adapter à ses besoins  
  $status = query_info();  
  }  
# boucle infinie, a stopper avec un kill     # tourne sas cesse jusqu'au ctrl+C
   
 
 
 
sub query_info {      
 
# Gestion du dialogue reseau
# Ouverture de la session TCP
 
  socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
  unless (connect(SERVER, sockaddr_in($MODBUS_PORT, $server_ip))) {
    print STDERR 'connexion au serveur "'.$server_ip.':'.$MODBUS_PORT.'" impossible'."\n";
    return 2;
  }
   
  my @adresses = qw(267 305);
  my %result;
 
  foreach (@adresses) {   ####
  $opt_mb_ad = $_;      ####
# Création de la requête    
  my $tx_hd_tr_id   = int(rand 65535);  
  my $tx_hd_length  = 6;  
  my $tx_hd_pr_id   = 0;  
  my $tx_buffer = pack("nnnCCnn", $tx_hd_tr_id, $tx_hd_pr_id , $tx_hd_length, $opt_unit_id, $opt_mb_fc, $opt_mb_ad, $opt_mb_nb);  
   
# Emission de la requête  
  send(SERVER, $tx_buffer, 0);  
   
# Attente d'une réponse  
  unless (can_read('SERVER', $opt_timeout)) {  
    close SERVER;  
    print STDERR 'receive timeout'."\n";  
    return 1;  
  }  
   
# Réception de l'entête  
  my ($rx_frame, $rx_buffer);  
  recv(SERVER, $rx_buffer, 7, 0);  
  $rx_frame = $rx_buffer;  
   
# Décodage de l'entête  
  my ($rx_hd_tr_id, $rx_hd_pr_id, $rx_hd_length, $rx_hd_unit_id) = unpack "nnnC", $rx_buffer;  
   
# Vérifie la cohérence de l'entête  
  unless (($rx_hd_tr_id == $tx_hd_tr_id) &&  
      ($rx_hd_pr_id == 0) &&  
      ($rx_hd_length < 256) &&  
      ($rx_hd_unit_id == 1)) {  
    close SERVER;  
    print STDERR 'error in receive frame'."\n";  
    return 1;  
  }  
   
# Réception du corps du message  
  recv(SERVER, $rx_buffer, $rx_hd_length-1, 0);  
  $rx_frame .= $rx_buffer;  
   
   
# Décodage du corps du message  
  my ($rx_bd_fc, $rx_body) = unpack "Ca*", $rx_buffer;  
   
# Vérification du statut d'exception  
  if ($rx_bd_fc > 0x80) {  
 
# Affichage du code exception  
    my ($rx_except_code) = unpack "C", $rx_body;  
    print 'exception (code '.$rx_except_code.')'."\n";  
  }  
 
  else {  
 
## Lecture de mot  
    my ($rx_bd_bc, $rx_read_word_data) = unpack "Ca*", $rx_body;  
 
# Lecture d'entier de 16 bits  
# un seul registre a lire d'ou le 'n'
    $result{$opt_mb_ad} = unpack 'n', $rx_read_word_data; ####
    }
    }
close SERVER;  
 # fin de la boucle foreach  ####
 # impression en console
 
  foreach (sort {$a <=> $b} (keys %result)) {
  print "<$_> : $result{$_};"
   
}
 print "\n";
 
 
########################" attente $timeout###################################
  sub can_read{
 my ($sock_handle, $timeout) = @_;
 my $hdl_select="";
 vec($hdl_select, fileno($sock_handle),1)=1;
 return (select($hdl_select, undef, undef, $timeout)==1);
}
############################################################################
 
 
# Affichage des valeurs recues  
 
sub disp_data {  
  my %result = @_;
  open(my $fh, ">>", 'C:/test.csv' ) || die ('Impossible d\'ouvrir le fichier "c:/test.csv"' );  
  print $fh "$_;$result{$_};" foreach (keys %result));  
  print $fh, "\n";
  close ($fh);
}
 
}

n°2221290
clubber43
Posté le 03-03-2014 à 11:08:56  profilanswer
 

PS,  
cela fait 15 jours que je n'ai pas pu refaire du code (deplacement etranger) du coup, j'ai eu le temps d'y regarder dans l'avion et le weekend ^^
 
Merci pour le coup de main
 
Ju

n°2221553
clubber43
Posté le 05-03-2014 à 14:43:45  profilanswer
 

Bon, j'ai resolu ms soucis, et du coup j'ai avancé le projet.  
 
A l'instant t, je veux maintenant exporter ces datas vers une base de données en SQL sur un serveur distant. J'ai créé une bdd avec MySql et je suis en train de chercher pour exporter mes valeurs jusqu'à cette base de données.
 
J'ai vu que l'on pouvait exporter ces datas à partir de requetes sql à partir d'un code en Perl. Deja, est-ce que j'ai juste, à savoir si l'on peux exporter ces datas avec les différents codes, et ensuite, si quelqu'un peux me donner un truc ou deux, je travaille de mon coté, mais je ne dis pas non contre un peu d'aide ^^
 
merci
 
ju

n°2221559
gilou
Modérateur
Modzilla
Posté le 05-03-2014 à 15:23:33  profilanswer
 

Pour interfacer Perl avec une BDD, rien de plus simple, il faut utiliser les modules DBI. http://dbi.perl.org/
C'est particulièrement simple et puissant.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221754
clubber43
Posté le 07-03-2014 à 08:58:59  profilanswer
 

Ok, je regarde tout ça.
 
Merci gilou

n°2221757
clubber43
Posté le 07-03-2014 à 09:06:54  profilanswer
 

Dans les docs, il parle beaucoup de Oracle mais peu de MySQL, je pense que les architectures sont semblables, et que je peux utiliser ça pour mes BdD MySQL du coup ?  
 
@+

n°2221782
clubber43
Posté le 07-03-2014 à 11:18:14  profilanswer
 

En cherchant sur les forums, j'ai trouvé ce genre de script.  
Je l'ai compilé à ma sauce, mais je ne vois pas trop comment je peux voir les data de ma base de données. :
 
 
#!/usr/bin/perl -w
use strict;
use DBI;
 
print "Content-type: text/html\n\n";
 
# Set up variables for the connection
my $server_name = 'localhost';
my $server_ip = '127.0.0.1:3306';
my $database_name = '';
my $database_user = 'root';
my $database_pass = 'admin';
 
my $DSN = 'driver={SQL Server};server=$server_name;tcpip=$server_ip;database=$database_name;uid=$database_user;pwd=$database_pass;';  
my $dbh = DBI->connect("dbi:ODBC:$DSN" ) || die "Couldn't open database: $DBI::errstr\n";
 
# Prepare the SQL query for execution
my $SQL1 = $dbh->prepare(<<End_SQL) || die "Couldn't prepare statement: $DBI::errstr\n";
select * FROM Test_Table
End_SQL
 
print '<table border="0" width="100%" cellpadding="0" cellspacing="0" bgcolor="#ffffff" summary=""><tr><td align="center">';
print '<table border="1" cellpadding="5" cellspacing="0" bgcolor="#ffffff" summary="">';
 
# Execute the query
$SQL1->execute() || die "Couldn't execute statement: $DBI::errstr\n";
 
# Fetch each row and print it
while ( my ($field1,$field2,$field3,$field4,$field5) = $SQL1->fetchrow_array() )  
{
     print "<tr><td>$field1</td><td>$field2</td><td>$field3</td><td>$field4</td><td>$field5</td></tr>";
}
 
print "</table></td></tr></table>";
 
# Disconnect from the database
$dbh->disconnect();

n°2221795
gilou
Modérateur
Modzilla
Posté le 07-03-2014 à 12:57:04  profilanswer
 

Ben après la query, les data sont récupérées en faisant $SQL1->fetchrow_array() c'est clair au vu du source.
 
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221797
clubber43
Posté le 07-03-2014 à 13:11:39  profilanswer
 

Ok, en fait je créé la connection avec la BDD puis, on prepare la requete et enfin, on l'envoie et on ferme l'acces a la BdD (disconnect).  
 
c'est un peu comme le progm précedent qaund on faisait une requete sur le serveur de données (compteur) et que l'on faisait un affichage de ces valeurs. Je commence à comprendre lol
 
+

n°2221798
gilou
Modérateur
Modzilla
Posté le 07-03-2014 à 13:14:20  profilanswer
 

>> Ok, en fait je créé la connection avec la BDD puis, on prepare la requete et enfin, on l'envoie
Puis on récupère les résultats (ligne à ligne en bouclant) et on les exploite
>> et on ferme l'acces a la BdD (disconnect).  
 
Oui, c'est une logique simple et standard.
 
A+,


Message édité par gilou le 07-03-2014 à 13:14:48

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221799
clubber43
Posté le 07-03-2014 à 13:34:01  profilanswer
 

Lorsque je lance le script, la fenetre me renvoie une erreur, de  
 
DBI Connect <....> failed unkown database at c:/ . . .  
connexion impossible à la bdd.
 
Ou faut-il placer la bdd pour que le script puisse l ouvrir ?  
 
++

n°2221803
gilou
Modérateur
Modzilla
Posté le 07-03-2014 à 13:59:54  profilanswer
 

Ben déjà c'est quoi ta base de donnée? et elle est en local?  
 
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221804
clubber43
Posté le 07-03-2014 à 14:07:23  profilanswer
 

c'est une base que j'ai créé en mysql et je souhaite la mettre en local avec Apache. j'ai installé apache sur mon pc et lorsque je le demarre, je peux aller sur la page http: localhost et sa m'affiche, bienvenue sur apache, .... de la pub ...
 
Je pense qu'il faut que je créé un dossier (www) dans le repertoire apache et que j'y mette tous les fichiers en .html, php, ... mais quid des fichier en .SQL  
 
@

n°2221811
gilou
Modérateur
Modzilla
Posté le 07-03-2014 à 14:33:56  profilanswer
 

Ben il va falloir que tu fasses quelque chose comme:
 
#!/usr/bin/perl
 
use strict;
use warnings; -w
use DBI;
 
 
my $host = 'localhost'; # ou '127.0.0.1'
my $port = 3306;
my $database = 'test'; # le nom de ta bdd
my $dsn = "DBI:mysql:database=$database;host=$host;port=$port";
 
my $user = 'root';  # pas une très bonne idée, ça, mais bon...
my $auth = 'admin';
my $dbh = DBI->connect($dsn, $user, $auth) || die "Database connection not made: $DBI::errstr";
 
.....
 
Edit: Mais je ne comprends pas ton dernier commentaire:
- Soit tu interroges la BDD MySQL directement avec un module perl DBI
- Soit tu interroges la BDD a travers Apache, mais il faut qu'il y ait des configurations spécifiques de modules en niveau de Apache pour qu'il interroge ta BDD (qui de toute façon, est toujours présente à priori [je suis pas spécialiste Apache, donc je ne sais pas s'il intègre directement une fonctionnalité BDD mais ce n'était pas la cas autrefois]), et dans ce cas la la réponse va te revenir sous forme d'une page html qu'il faudra que tu parses.
 
A+,


Message édité par gilou le 07-03-2014 à 14:43:59

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221812
clubber43
Posté le 07-03-2014 à 14:36:49  profilanswer
 

OK,  
je garde la même philosophe que pour le script précédent, et je refait le bout du pgrm avec connection, requete, ...
 
Merci bien pour le coup de main

n°2221814
gilou
Modérateur
Modzilla
Posté le 07-03-2014 à 14:44:25  profilanswer
 

cf mon edit.  
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2221818
clubber43
Posté le 07-03-2014 à 15:00:35  profilanswer
 

J'ai saisis.
 
En fait, je vais utiliser exclusivement le PERL pour lire mes valeurs dans le compteur et l'exporter via les requetes dans la BdD SQL que j'ai créé.
 
Apache est utilisé pour un autre application. J'ai un peu mélangé les affaires.  
 
Merci et bon weekend,  
je travailelrais un plus cela ce soir à tete reposée.
 
@+
 
Pour lire les valeurs, j'utilise le module DBI qui me

n°2222049
clubber43
Posté le 11-03-2014 à 09:16:34  profilanswer
 

Voila un bout de code pour créer une BDD energie :
 
#!/usr/bin/perl  
 
use strict;  
use warnings; -w  
use DBI;  
 
 
my $dbh = DBI->connect(dbi:mysql:cours", 'scott', 'tiger');
 
#creation table ->energie<-
 
$dbh->do ("create table energie(
id_compteur number(10) not null primary key,
puissance_P number(10),
puissance_Q number(10),
courant_In number (10),
time timestamp(20))" ) or die "Probleme creation table::$DBI::errstr";
 
#preparation
my $ins = $dbh->prepare("insert into energie values(1,2,3,4,5)" );
 
my $compteur=0;
 
print " Entrez une valeur, terminez par Ctr-D \n";
 
while (my $lugne = <> )
{
my ($puissance_P, $puissance_Q) = split (/\ t/, $ligne);
 
#Execution
$ins->execute($compteur, $puissance_P, $puissance_Q) or die "pb à l insertion";
$compteur++;
}
 
$ins->finish;
$dbh-> disconnect;
 
J'ai des erreurs de compils, mais j'ai retourné le probleme et je ne comprend pas forcement les erreurs .  .  .
 
Merci de m'aider ^^

n°2222050
clubber43
Posté le 11-03-2014 à 09:20:47  profilanswer
 

Pour la lecture, j'ai codé un bout aussi et installer le script dbi-lib.pl
 
#!/usr/bin/perl
require "cgi-lib.pl";
 
# précise qu'il faut utiliser DBI
eval('use DBI;');
 
# défini dans quel répertoire est le BDD
$dbase_dir = "/www/energie";
 
# permet de spécifier le content type
print &PrintHeader;
 
# je spécifie ma requete en SQL normal
$sql_liste_compteur = "select id_compteur, nom_compteur from categori order by nom_ccompteur";
 
# J'effectue la connexion DB et si ca ne marche pas j'imprime un message d'erreur
my $dbh = DBI->connect("DBI:XBase:$dbase_dir" )  
 or print "Connection a la DB impossible\n";
 
 
# en utilisant mon identifiant de la connexion, je prépare la requete
# SQL a effectuer. En cas d'erreur d'imprime un message
my $sth = $dbh->prepare($sql_liste_compteur)  
 or print "prepare error :  $dbh->errstr()";
 
# On va maintenant exécuter a proprement parler la requete SQL  
$sth->execute() or print "execute error : $sth->errstr()";
$premier=1;
 
# $sth->fetchrow_array permet de récupérer 1 par 1 les différents
# enregistrements trouvés par la requete SQL.
# On copie le contenu de l'enregistrement dans le tableau @catégories
while (@categories = $sth->fetchrow_array)
{
# le if sert uniquement a afficher un titre si c'est notre premier
# passage dans la boucle
        if ($premier == 1)
        {       print "<hr>Liste des catégories : <br><br>\n";
                $premier = 0;
        }
        # je récupères la valeur des champs de cet enregistrement. Les
        # champs sont stockés dans le tableau, dans le même ordre que
        # ce que la requete SQL a indiqué.
        # $categories[0] contient donc id_compteur
        # $categories[1] contient donc nom_ccompteur
        ($id_compteur, $nom_compteur) = @categories;
 
        # Il ne reste plus qu'a les imprimer à l'écran
        print <<ENDHTML;
        $id_cat : $nom_caompteur<br>
ENDHTML
 
}
 
# on se déconnecte
$dbh->disconnect;
 
 
Et là, je retrouve des erreurs de compil . . .  
 
@+

n°2222064
clubber43
Posté le 11-03-2014 à 14:28:52  profilanswer
 

Bon, j'ai refaits un morceau de code et j'ai des erreurs du type :
Can't find string terminator at line 28,
Malformed UTF-8 Character byte 0x20 at line 19 19 24 24 27  

Code :
  1. #!/usr/bin/perl
  2. use warnings;
  3. use strict;
  4. use Encode;
  5. use utf8;
  6. use DBI;            # Charger le module DBI
  7.  
  8.  
  9. ActiverAccents();
  10.  
  11. # Paramètres de connection à la base de données
  12. my $bd        = 'Energie';
  13. my $serveur    = 'localhost'; # @ IP IP
  14. my $identifiant = 'root';      # identifiant  
  15. my $motdepasse    = 'admin';
  16. my $port    = '';        #Si vous ne savez pas, ne rien mettre
  17.  
  18. # Connection à la base de données mysql
  19. print "Connexion à la base de données $bd\n";
  20. my $dbh = DBI->connect( "DBI:mysql:database=$bd;host=$serveur;port=$port",  
  21.    $identifiant, $motdepasse, {  
  22.     RaiseError => 1,
  23.    }  
  24. ) or die "Connection impossible à la base de données $bd !\n $! \n $@\n$DBI::errstr";
  25.  
  26. # Création des tables
  27. print "Création de la table COMPTEUR\n";
  28. my $sql_creation_table_compteur = <<"SQL";
  29.  id_compteur    INT             NOT NULL ,
  30.  emplacement      VARCHAR( 10 )   NOT NULL ,
  31.  batiment    VARCHAR( 10 )   NOT NULL ,
  32.  niveau     VARCHAR( 10 )   NOT NULL ,
  33.  PRIMARY KEY ( id_compteur )
  34. )  COMMENT = 'COMPTEUR';
  35. SQL
  36.  
  37. $dbh->do('DROP TABLE IF EXISTS compteur;') or die "Impossible de supprimer la table compteur\n\n";
  38. $dbh->do($sql_creation_table_compteur) or die "Impossible de créer la table compteur\n\n";
  39.  
  40. print "Création de la table Releves\n";
  41. my $sql_creation_table_releves = <<"SQL";
  42. CREATE TABLE releves (
  43.  id_compteur      INT               NOT NULL  AUTO_INCREMENT PRIMARY KEY COMMENT 'Elle sera générée automatiquement.',
  44.  puissance_p      INT          NOT NULL ,
  45.  puissance_q      INT          NOT NULL ,
  46.  courant_I      INT          NOT NULL ,  
  47. ) COMMENT = 'COMPTEUR';
  48. SQL
  49.  
  50. $dbh->do('DROP TABLE IF EXISTS releves;') or die "Impossible de supprimer la table releves\n\n";
  51. $dbh->do($sql_creation_table_releves) or die "Impossible de créer la table releves\n\n";
  52.  
  53.  
  54. # Insertion des données
  55. my $requete_sql_compteur = <<"SQL";
  56.  INSERT INTO rcompteur ( id_compteur, emplacement, batiment, niveau)
  57.  VALUES ( 1, TDD1, D, 1);
  58. SQL
  59.  
  60. close $fh_regions;
  61.  
  62.  
  63. # Déconnection de la base de données
  64. $dbh->disconnect();
  65.  
  66.  
  67. sub ActiverAccents {
  68.    my $encodage;
  69.    # Windows
  70.      if ( lc($^O ) eq 'mswin32') {
  71.     eval {
  72.         my ($codepage) = ( `chcp` =~ m/:\s+(\d+)/ );
  73.         $encodage = "cp$codepage";
  74.         foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {
  75.         binmode $h, ":encoding($encodage)";
  76.         }
  77.     };
  78.    }
  79.    else {
  80.     $encodage = `locale charmap`;
  81.     eval {
  82.         foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {
  83.         binmode $h, ":encoding($encodage)";
  84.         }
  85.     };
  86.    }
  87.  return $encodage;
  88. }


Message édité par gilou le 11-03-2014 à 20:19:33
n°2222079
clubber43
Posté le 11-03-2014 à 16:55:39  profilanswer
 

Personne pour me sortir de mon chantier  :ange:  
 
J'ai reussi à trouver un tuto pour les script en PERl mais rien qui ne repond aux erreurs ci dessus  . . .  
 
 
@+

n°2222088
gilou
Modérateur
Modzilla
Posté le 11-03-2014 à 20:21:59  profilanswer
 

> Malformed UTF-8 Character byte 0x20 at line 19 19 24 24 27  
Ben tes erreurs viennent de ce que tu as des é accentués sans être sous un éditeur en utf-8 pour les saisir.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2222092
clubber43
Posté le 11-03-2014 à 21:27:18  profilanswer
 

Alors ça, c'est une erreur c** . . .  
 
Parcontre, pour le cant find string, c'est aussi une erreur du même niveau ^^ OU alors un peu plus poussé ?  
 
MErci gilou

n°2222093
gilou
Modérateur
Modzilla
Posté le 11-03-2014 à 22:08:05  profilanswer
 

L'autre erreur, c'est parce que ton SQL terminal est suivi d'un blanc.
Or il doit être exactement identique a ce qui était dans le <<"...";
Donc enlèves ce blanc (en laissant le blanc et en remplaçant <<"SQL"; par <<"SQL "; ça marchera aussi mais ce n'est pas une bonne solution)
A+,


Message édité par gilou le 11-03-2014 à 22:10:12

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°2222102
clubber43
Posté le 12-03-2014 à 08:04:05  profilanswer
 

A ok,  
je refaits le script ce matin et je le posterais après ^^
 
Merci
@+

n°2222104
clubber43
Posté le 12-03-2014 à 08:34:22  profilanswer
 

C'est parfait, je n'ai plus d'erreur de compilation,  
Du coup mon script tourne, il me retse juste une erreur de : DBI Connect failed, unkown database at line 20.
 
Je pense que mon script ne reconnais pas la base de données.
Je continue mes investigations  :)  
 
Meric

n°2222113
clubber43
Posté le 12-03-2014 à 10:49:37  profilanswer
 

BON !!
Les problèmes de connexions et d'erreurs sont OK, je compile le code et là, j'ai un message :
 
DBD::mysql::db do failed you have an error in your SQL synthax à line 37, check the manual . . .  
DBD::mysql::db do failed you have an error in your SQL synthax à line 37, check the manual . . .  
 
pourtant, le script parait juste :
 

Code :
  1. #!/usr/bin/perl
  2. use warnings;
  3. use strict;
  4. use Encode;
  5. use utf8;
  6. use DBI;            # Charger le module DBI
  7.  
  8.  
  9. ActiverAccents();
  10.  
  11. # Paramètres de connection à la base de données
  12. my $bd        = 'Energie';
  13. my $serveur    = '127.0.0.1'; # @ IP IP
  14. my $identifiant = 'root';      # identifiant  
  15. my $motdepasse    = 'admin';
  16. my $port    = '3306';        #Si vous ne savez pas, ne rien mettre
  17.  
  18. # Connection à la base de données mysql
  19. print "Connexion a la base de donnees $bd\n";
  20. my $dbh = DBI->connect( "DBI:mysql:database=$bd;host=$serveur;port=$port",  
  21.    $identifiant, $motdepasse, {  
  22.     RaiseError => 1,
  23.    }  
  24. ) or die "Connection impossible a la base de donnees $bd !\n $! \n $@\n$DBI::errstr";
  25.  
  26. # Création des tables
  27. print "Creation de la table COMPTEUR\n";
  28. my $sql_creation_table_compteur = <<"SQL";
  29.  id_compteur    INT             NOT NULL PRIMARY KEY ,
  30.  emplacement      VARCHAR( 10 )   NOT NULL ,
  31.  batiment    VARCHAR( 10 )   NOT NULL ,
  32.  niveau     VARCHAR( 10 )   NOT NULL )
  33. COMMENT = 'COMPTEUR';
  34. SQL
  35.  
  36. $dbh->do('DROP TABLE IF EXISTS compteur;') or die "Impossible de supprimer la table compteur\n\n";
  37. $dbh->do($sql_creation_table_compteur) or die "Impossible de creer la table compteur\n\n";
  38.  
  39. print "Creation de la table Releves\n";
  40. my $sql_creation_table_releves = <<"SQL";
  41. CREATE TABLE releves (
  42.  id_compteur      INT               NOT NULL  AUTO_INCREMENT PRIMARY KEY COMMENT #Elle sera generee automatiquement,
  43.  puissance_p      INT          NOT NULL ,
  44.  puissance_q      INT          NOT NULL ,
  45.  courant_I      INT          NOT NULL )
  46. COMMENT = 'COMPTEUR';
  47. SQL
  48.  
  49. $dbh->do('DROP TABLE IF EXISTS releves;') or die "Impossible de supprimer la table releves\n\n";
  50. $dbh->do($sql_creation_table_releves) or die "Impossible de creer la table releves\n\n";
  51.  
  52.  
  53. # Insertion des données
  54. my $requete_sql_compteur = <<"SQL";
  55.  INSERT INTO rcompteur ( id_compteur, emplacement, batiment, niveau)
  56.  VALUES ( 1, TDD1, D, 1);
  57. SQL
  58.  
  59. # Deconnection de la base de donnees
  60. $dbh->disconnect();
  61.  
  62.  
  63. sub ActiverAccents {
  64.    my $encodage;
  65.    # Windows
  66.      if ( lc($^O ) eq 'mswin32') {
  67.     eval {
  68.         my ($codepage) = ( `chcp` =~ m/:\s+(\d+)/ );
  69.         $encodage = "cp$codepage";
  70.         foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {
  71.         binmode $h, ":encoding($encodage)";
  72.         }
  73.     };
  74.    }
  75.    else {
  76.     $encodage = `locale charmap`;
  77.     eval {
  78.         foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {
  79.         binmode $h, ":encoding($encodage)";
  80.         }
  81.     };
  82.    }
  83.  return $encodage;
  84. }


Message édité par gilou le 12-03-2014 à 12:08:28
mood
Publicité
Posté le   profilanswer
 

 Page :   1  2  3  4  5  6  7

Aller à :
Ajouter une réponse
 

Sujets relatifs
Copier données en ligne par colonneComment génerer un fichier csv à partir d'une base de données?
perl + xml[Perl] Créer un graph RRD avec RRDTool::OO
[Résolu][Perl] XML::DOM Comment avoir une belle indentation?Programmation Java lecture base de données
[VBA-Excel] Comment appeler un fichier pour récupérer des données ?extraction de donnees
Récupération données d'un site PHPRécupérer des données d'un fichier xml
Plus de sujets relatifs à : [Résolu] Export données en perl


Copyright © 1997-2022 Hardware.fr SARL (Signaler un contenu illicite / Données personnelles) / Groupe LDLC / Shop HFR