Lecture carte SD

Bonjour,
je vous explique mon problème, je dois envoyer des données de mon Arduino Méga + Shield Ethernet vers une BDD. Jusque la pas de soucis, mais lorsque il y a une coupure réseau je stock les données dans une carte SD et quand je récupère le réseau je lis les données stockées ligne par ligne pour les envoyer avec un GET vers mon script PHP et les stocker dans ma BDD.
Le problème est que quand je lis les données ligne par ligne avec readStringUntil('\n') j’ai l’impression qu’il rajoute quelque chose ou change le format ou je ne sais pas quoi mais ca pose problème au script php parce que rien n’arrive sur ma BDD.

ichierTempon=SD.open("tempon.txt");
          if(fichierTempon)
          {
            Serial.println("fichierTempon.txt");
            while(fichierTempon.available())
            {
              messageTempon=fichierTempon.readStringUntil('\n');
              client.print( "GET /test/tmp.php?");
              client.print(messageTempon);
              client.println( " HTTP/1.1");
              client.println( "Host: 192.167.5.19" );
              client.println( "Content-Type: application/x-www-form-urlencoded" );
              client.println( "Connection: close" );
              client.println();
              client.println();
              client.stop();
              Serial.println(messageTempon);
              delay(500);
            }
            fichierTempon.close();
            SD.remove("tempon.txt");

Le messageTempon est pourtant bien écris quand je l’affiche sur le moniteur série.
Si je recopie le contenu messageTempon client.print("&valeur1=1.4&valeur2=45.45...." ca fonctionne, l’envoi ce fait bien.
Du coup je ne comprend pas ce qui pourrait être le problème lorsqu’il lit dans le carte SD (je ne dépasse le nombre de caractère pour un GET)
J’espère que vous comprendrai mon problème si pas n’hésitez pas à me demander des précisions, merci d’avance.

Quand vous stockez sur votre carte SD, vous utilisez println() ? --> si oui vous insérez 2 caractères en fin de ligne un '\r' suivi d'un '\n'. L'appel à la fonction fichierTempon.readStringUntil('\n'); va lire jusqu'au '\n' (et se débarrasser du '\n') mais le '\r' sera bien dans la chaîne lue et vous le balancez ensuite dans le GET. comme c'est un caractère qui ne se voit pas, quand vous faites le print dans la console vous ne voyez rien.

Pour voir ce qu'il en est vraiment je vous propose de remplacer Serial.println(messageTempon); par

    char* ptr = (char*) messageTempon.c_str();
    while (*ptr) {
      Serial.print("[0x"); Serial.print(byte (*ptr), HEX); Serial.println("]");
      ptr++;
    }

si vous voyez à la fin du texte un [0xD] c'est que vous aviez bien ce caractère en plus.

il existe une fonction qui s'appelle [url=https://www.arduino.cc/reference/en/language/variables/data-types/string/functions/trim/]trim()[/url] que vous pouvez appeler sur la String (messageTempon.trim();) et qui va nettoyer tout ce qui correspond à un espace en début et en fin de chaîne. Pour déterminer si un caractère est un espace, cette méthode appelle la fonction standard [url=https://en.cppreference.com/w/cpp/string/byte/isspace]isspace()[/url] qui détecte les espaces, tabulations mais aussi le '\r' qui pourrait vous ennuyer.

idéalement il ne faudrait pas le mettre dans votre fichier tampon. pour cela utilisez un file.print() pour écrire vos données au lieu de println() puis, comme il faut rajouter quand même le '\n' faites un file.write('\n');. Comme ça votre fichier n'aura pas de '\r' qui traîne

ps: on dit tampon pas tempon

Merci beaucoup j'essaye ca demain et vous tient au courant.
Bonne journée.

Bonjour, j’ai fais ceci :

char* ptr = (char*) messageTampon.c_str();
    while (*ptr) {
      Serial.print("[0x"); Serial.print(byte (*ptr), HEX); Serial.println("]");
      ptr++;
    }

et j’obtiens bien [0xD] à la fin.
J’ai essayé de mettre ‘\n’ et ‘\r’ en fin de ligne quand même mais ca ne fonctionne pas non plus.

Je viens de trouver la solution, j’ai mis fichierTampon.print('\n'); à la place de FichierTampon.println(); comme vous m’avez dis et ca fonctionne…

Vous savez qu’elle est la différence entre les deux? Parce que j’avais quand même un 0XD en fin de fichier donc le passage a la ligne ce faisait bien?
Merci beaucoup!

Felicien9:
Je viens de trouver la solution, j’ai mis fichierTampon.print('\n'); à la place de FichierTampon.println(); comme vous m’avez dis et ca fonctionne…

j’aime bien le “je viens de trouver…” :slight_smile:

Felicien9:
Vous savez qu’elle est la différence entre les deux? Parce que j’avais quand même un 0XD en fin de fichier donc le passage a la ligne ce faisait bien?

Oui je vous l’ai expliqué au tout début de ma réponse #1

Ha oui, merci.
Savez-vous pourquoi la connexion ce fait qu’une seule fois vers le serveur php?

for(j=0; j<=nbBalanceMax; j++)  
   {
    if(balances[j]==1) 
    {  
      if (client.connect("X.X.X.X",80)) 
      {
        if(tampon==1)
        {
          fichierTampon=SD.open("tampon.txt");
          if(fichierTampon)
          {
            Serial.println("fichierTampon.txt");
            while(fichierTampon.available())
            {
              messageTampon=fichierTampon.readStringUntil('\n');
              client.print("GET /test2_DIEU/tmp.php?");
              client.print(messageTampon);
              client.println( " HTTP/1.1");
              client.println( "Host: X.X.X.X" );
              client.println( "Content-Type: application/x-www-form-urlencoded" );
              client.println( "Connection: close" );
              client.println();
              client.println();
              client.stop();
              Serial.println(messageTampon);
              delay(500);
            }
            fichierTampon.close();
            SD.remove("tampon.txt");
          }
          else{
            Serial.println("erreur d ouverture fichier");
          }

Même lorsque je mets le client.stop après la boucle, la connexion ce fait qu’une seul fois …
Merci d’avance.