Problema al mandar imágenes con GPRS Shield

Hola gente!!! :) :)

Es mi primer proyecto con arduino y mi primer post aquí y ha llegado el punto en el que no se como seguir avanzando. He realizado una estación meteorológica y control automático de riego mediante diversos sensores y una web en la cual mediante charts de google controlo todo. La pagina en si, por si alguien esta interesado en visitarla, es mete-o.es. Aviso que aun esta en construcción. xDDDDD

Bueno ahí va mi duda: Quiero enviar fotos desde arduino a mi base de datos MySQL y mostrarlas en la web. La foto la realizo desde una cámara TTL. Posteriormente en arduino transformo la imagen a un archivo enviable a MySQL. El tema de recepción y guardado de la imagen en si lo tengo dominado. Mi duda surge en el momento de enviar la foto por el modulo GPRS. Via WiFi no hay problema ya que no tiene mucha complejidad en si, el problema es enviarlo por el GPRS shield ya que son comandos AT, los cuales desconozco bastante.

Si alguien controla este tema y me puede ayudar o aconsejar en cambiar el siguiente código en comandos AT estaría agradecido de por vida. xDDD

if (client.connected()) {
      Serial.println(F("Connected !"));
      client.println(F("POST /arduino-camera-wifi/camera.php HTTP/1.1"));
      client.println(F("Host: 192.168.0.1:80"));
      client.println(F("Content-Type: multipart/form-data; boundary=AaB03x"));
      client.print(F("Content-Length: "));
      client.println(len);
      client.print(start_request);
            
      // Read all the data up to # bytes!
      byte wCount = 0; // For counting # of writes
      while (jpglen > 0) {
        
        uint8_t *buffer;
        uint8_t bytesToRead = min(64, jpglen); // change 32 to 64 for a speedup but may not work with all setups!
        
        buffer = cam.readPicture(bytesToRead);
        client.write(buffer, bytesToRead);
    
        if(++wCount >= 64) { // Every 2K, give a little feedback so it doesn't appear locked up
          Serial.print('.');
          wCount = 0;
        }
        jpglen -= bytesToRead; 
      }
      
      client.print(end_request);
      client.println();
      
  Serial.println("Transmission over");
  } 
  
  else {
      Serial.println(F("Connection failed"));    
    }
    
     while (client.connected()) {

      while (client.available()) {

    // Read answer
        char c = client.read();
        Serial.print(c);
        //result = result + c;
      }
    }
    client.close();

Por si sirve de ayuda el envío de los datos de los sensores lo hago de esta manera y funciona perfectamente:

//Inica protocolo GPRS.
              gprsSerial.println("AT+CGATT?");
              delay(100);
              toSerial();    
              //Incia protocolo http.
              gprsSerial.println("AT+CGATT?");
              delay(100);
              toSerial();
              //Configuracion interna
              gprsSerial.println("AT+SAPBR=3,1,\"CONTYPE\",\"GPRS\"");
              delay(1000);
              toSerial();
              //Configuracion interna. Configura APN con la compañia movil.
              gprsSerial.println("AT+SAPBR=3,1,\"APN\",\"orangeworld\"");
              delay(1000);
              toSerial();
              //Configuracion interna.
              gprsSerial.println("AT+SAPBR=1,1");
              delay(1000);
              toSerial();
              gprsSerial.println("AT+HTTPINIT");
              delay(1000); 
              toSerial();
              //La funcion gprsSerial.println no admite enteros, con lo cual hay que pasar el int a String           para que no de error al cargarlo.
              String temperaturaS = String(temperatura);
              // set http param value
              gprsSerial.println("AT+HTTPPARA=\"URL\",\"http://mete-o.ddns.net/temp.php?val=" + temperaturaS + "\"");  
              delay(1000);
              toSerial();
              //Acciones type 0 = GET, 1 = POST, 2 = HEAD para la secuencia AT+HTTPACTION. Con GET envia datos a la URL.
              gprsSerial.println("AT+HTTPACTION=1");
              delay(5000);
              toSerial();
              //Comprueba que el servidor esta conectado.
              gprsSerial.println("AT+HTTPREAD"); 
              delay(100);
              toSerial();
              gprsSerial.println("");
              gprsSerial.println("AT+HTTPTERM");
              toSerial();
              delay(100);
              gprsSerial.println("");
              delay(100);

Entiendo que cada client.print(); equivale a un comando AT especifico según quieras hacer. Eso justamente es lo que desconozco.

Muchas gracias de ante mano a todos. ;)

Bueno, comienza con una lectura de las normas del foro y luego edita los códigos que has posteado y el enlace para que alguién pueda hacer click y dirigirse a el directamente.

Busca en el foro video gprs y algo vas a encontrar, me refiero a que uses Search (arriba derecha).

Ya está arreglado lo del link y los códigos. He buscado por todos sitios y no he encontrado nada. Créeme que no pediría ayuda si no fuese necesario. Gracias.

Que GSM shield usas?

para enviar mucha data (imagen) por GPRS generalmente se hace por paquetes y se reconstruye despues todo en el server, el tamaño depende de la resolucion/settings y compresion de la imagen de la camara serial, entre 100k y 400k

investiga si el modulo soporta UDP modo transparente (pass-trhu), en el cual solo tienes que recibir data de la camara y enviar tantos frames como sean recibidos.

cuando tengas la data en el server te puedo pasar unos .exe para reconstruirla si no es que ya lo tienes hecho

Prueba con esta guia TCP connection over GPRS o este upload/downlaod file from FTP using AT commands (Sim900 + arduino)

Gracias por las respuestas. Estudiaré los enlaces que me manda Surbyte y comento los resultados.

Lo muevo a Software!

He mirado y remirado los post que me pasaste surbyte. El problema es que son para un servidor FTP.
He encontrado algo parecido pero con WiFi, y funciona bastante bien. Lo que pasa es que yo la instalación la tendré en el campo, donde no hay Wifi. Luego encontré uno con el cual envían e-mails.
Comparto los links de los tutoriales a ver si se os ocurre alguna idea.

Link para enviar e-mail:

http://chrisbird.synthasite.com/remote-camera.php

Luego el link del tutorial donde lo hacen con WiFI, el cual probé y funciona perfectamente.

Link para enviar fotos por WiFi:

https://www.openhomeautomation.net/wireless-camera/

La idea es mas o menos como este ultimo link pero con comandos AT. Si alguien que entienda de estos y quiera explicarme que comandos usar le estaría agradecido.

Mi código usado en este momento es el siguiente:

#include <SoftwareSerial.h>
#include <String.h>
#include <DHT11.h>
#include <SPI.h>

SoftwareSerial mySerial(7, 8);


//Declaracion de variables. 
int pin=6; 
DHT11 dht11(pin);                    
int cuenta=0;
int error_DHT; 
float temperatura;
float humedad_ambiente;

//Variables para filtro de paso bajo de temperatura.
int lecturast[10]; // Array para almacenar lecturas
int lecturaActualt = 0; // Lectura por la que vamos
int totalt = 0; // Total de las que llevamos
int mediat = 0; // Media de las medidas

//Variables para filtro de paso bajo de humedad ambietal.
int lecturasha[10]; // Array para almacenar lecturas
int lecturaActualha = 0; // Lectura por la que vamos
int totalha = 0; // Total de las que llevamos
int mediaha = 0; // Media de las medidas




void setup()
 {
     mySerial.begin(19200);             
     Serial.begin(19200);    
     InicioSensortemperatura(); // Iniciamos el sensor de temperatura.
     InicioSensorhumedad_ambiente(); // Iniciamos el sensor de humedad.        
 }



 
void loop()
 {     
      
        //Comprobación de la lectura del DHT11. Si devuelve 0 es que ha leido bien.        
        if((error_DHT = dht11.read(humedad_ambiente, temperatura)) == 0)   
          {
            //Inica protocolo GPRS.
            mySerial.println("AT+CGATT?");
            delay(100);
            toSerial();    
            //Incia protocolo http.
            mySerial.println("AT+CGATT?");
            delay(100);
            toSerial();
            //Configuracion interna
            mySerial.println("AT+SAPBR=3,1,\"CONTYPE\",\"GPRS\"");
            delay(1000);
            toSerial();
            //Configuracion interna. Configura APN con la compañia movil.
            mySerial.println("AT+SAPBR=3,1,\"APN\",\"orangeworld\"");
            delay(1000);
            toSerial();
            //Configuracion interna.
            mySerial.println("AT+SAPBR=1,1");
            delay(1000);
            toSerial();
            mySerial.println("AT+HTTPINIT");
            delay(1000); 
            toSerial();
            //La funcion mySerial.println no admite enteros, con lo cual hay que pasar el int a String para que no de error al cargarlo.
            String temperaturaS = String(temperatura);
            mySerial.println("AT+HTTPPARA=\"URL\",\"http://mete-o.ddns.net/envio/temp.php?val=" + temperaturaS + "\"");  
            delay(1000);
            toSerial();
            //Acciones type 0 = GET, 1 = POST, 2 = HEAD para la secuencia AT+HTTPACTION. Con GET envia datos a la URL.
            mySerial.println("AT+HTTPACTION=1");
            delay(5000);
            toSerial();
            //Comprueba que el servidor esta conectado.
            mySerial.println("AT+HTTPREAD"); 
            delay(100);
            toSerial();
            mySerial.println("");
            mySerial.println("AT+HTTPTERM");
            toSerial();
            delay(100);
            mySerial.println("");
            delay(100);     
             //Inica protocolo GPRS.
            mySerial.println("AT+CGATT?");
            delay(100);
            toSerial();    
            //Incia protocolo http.
            mySerial.println("AT+CGATT?");
            delay(100);
            toSerial();
            //Configuracion interna
            mySerial.println("AT+SAPBR=3,1,\"CONTYPE\",\"GPRS\"");
            delay(1000);
            toSerial();
            //Configuracion interna. Configura APN con la compañia movil.
            mySerial.println("AT+SAPBR=3,1,\"APN\",\"orangeworld\"");
            delay(1000);
            toSerial();
            //Configuracion interna.
            mySerial.println("AT+SAPBR=1,1");
            delay(1000);
            toSerial();
            mySerial.println("AT+HTTPINIT");
            delay(1000); 
            toSerial();
            //La funcion mySerial.println no admite enteros, con lo cual hay que pasar el int a String para que no de error al cargarlo.
            String humedad_ambienteS = String(humedad_ambiente);
            mySerial.println("AT+HTTPPARA=\"URL\",\"http://mete-o.ddns.net/envio/hum.php?val=" + humedad_ambienteS + "\"");  
            delay(1000);
            toSerial();
            //Acciones type 0 = GET, 1 = POST, 2 = HEAD para la secuencia AT+HTTPACTION. Con GET envia datos a la URL.
            mySerial.println("AT+HTTPACTION=1");
            delay(5000);
            toSerial();
            //Comprueba que el servidor esta conectado.
            mySerial.println("AT+HTTPREAD"); 
            delay(100);
            toSerial();
            mySerial.println("");
            mySerial.println("AT+HTTPTERM");
            toSerial();
            delay(100);
            mySerial.println("");
            delay(100);   
          }
         else 
            {
               Serial.println("Error al leer el sensor DHT11....");
            }                    
       
                                             
       
       // Repetición del bucle cada 1 segundos.
       delay(5000);                                              
  }


/*.........--------------FUNCIONES--------------.........*/

/**** Inicializa el sensor de temperatura ****/
void InicioSensortemperatura() 
 {
   for (int i = 0; i < 10; i++) //Inicializamos array para temperatura.
     {
  lecturast[i] = 0;
     }
 }

/**** Función de lectura con filtro paso bajo por software para temperatura. ****/
void lecturaSensortemperatura() 
 {
// Eliminando la última muestra
totalt = totalt - lecturast[lecturaActualt];

// Lectura pin digital 6
int valorA1 = temperatura;

lecturast[lecturaActualt] = valorA1;

// Añadimos la lectura al total
totalt = totalt + lecturast[lecturaActualt];

// Incrementamos el índice del array
lecturaActualt = lecturaActualt + 1;

// Comprabamos que no nos salimos del tamaño del array
if (lecturaActualt >= 10)
{
  lecturaActualt = 0;
}

// Calculamos la media
temperatura = totalt / 10;    
 }

/**** Inicializa el sensor de temperatura ****/
void InicioSensorhumedad_ambiente() 
 {
   for (int i = 0; i < 10; i++) //Inicializamos array para humedad ambiente.
     {
  lecturasha[i] = 0;
     }
 }

/**** Función de lectura con filtro paso bajo por software para la humedad ambiente. ****/
void lecturaSensorhumedad_ambiente() 
 {
// Eliminando la última muestra
totalha = totalha - lecturasha[lecturaActualha];

// Lectura pin digital 6
int valorA1 = humedad_ambiente;

lecturasha[lecturaActualha] = valorA1;

// Añadimos la lectura al total
totalha = totalha + lecturasha[lecturaActualha];

// Incrementamos el índice del array
lecturaActualha = lecturaActualha + 1;

// Comprabamos que no nos salimos del tamaño del array
if (lecturaActualha >= 10)
{
  lecturaActualha = 0;
}

// Calculamos la media
humedad_ambiente = totalha / 10;    
 }

void toSerial()
 {
  while(mySerial.available()!=0) Serial.write(mySerial.read());
 }

Lo que te pase es para un servidor FTP pero la idea es transferir datos, datos pueden ser una imagen, una archivo que tienes en una SD y ambos se transfieren por TCP o UDP. El caso es el mismo.
El video te muestra como transferir información y creo que deberia servirte para tu proyecto.

Lo que dices que hace este hombre en su tutorial es lo siguiente:

void setup(){

    pinMode(onModulePin, OUTPUT);
    Serial.begin(115200);


    Serial.println("Starting...");
    power_on();

    delay(5000);

    Serial.println("Connecting to the network...");

    while( (sendATcommand("AT+CREG?", "+CREG: 0,1", 500)
            || sendATcommand("AT+CREG?", "+CREG: 0,5", 500)) == 0 );

    configure_FTP();

    uploadFTP();

    Serial.print("Incoming data: ");
    Serial.println(incoming_data);
}
.
.
.
.
.

void configure_FTP(){

    sendATcommand("AT+SAPBR=3,1,"Contype","GPRS"", "OK", 2000);
    sendATcommand("AT+SAPBR=3,1,"APN","APN"", "OK", 2000);
    sendATcommand("AT+SAPBR=3,1,"USER","user_name"", "OK", 2000);
    sendATcommand("AT+SAPBR=3,1,"PWD","password"", "OK", 2000);

    while (sendATcommand("AT+SAPBR=1,1", "OK", 20000) != 1);
    sendATcommand("AT+FTPCID=1", "OK", 2000);
    sendATcommand("AT+FTPSERV="ftp.yourserver.com"", "OK", 2000);
    sendATcommand("AT+FTPPORT=21", "OK", 2000);
    sendATcommand("AT+FTPUN="user_name"", "OK", 2000);
    sendATcommand("AT+FTPPW="password"", "OK", 2000);

}




void uploadFTP(){

    sendATcommand("AT+FTPPUTNAME="file_name"", "OK", 2000);
    sendATcommand("AT+FTPPUTPATH="/path"", "OK", 2000);
    if (sendATcommand("AT+FTPPUT=1", "+FTPPUT:1,1,", 30000) == 1)
    {
        data_size = 0;
        while(Serial.available()==0);
        aux = Serial.read();
        do{
            data_size *= 10;
            data_size += (aux-0x30);
            while(Serial.available()==0);
            aux = Serial.read();
        }
        while(aux != 0x0D);

        if (data_size >= 100)
        {
            if (sendATcommand("AT+FTPPUT=2,100", "+FTPPUT:2,100", 30000) == 1)
            {
                Serial.println(sendATcommand(test_str, "+FTPPUT:1,1", 30000), DEC);
                Serial.println(sendATcommand("AT+FTPPUT=2,0", "+FTPPUT:1,0", 30000), DEC);
                Serial.println("Upload done!!");
            }
            else
            {
                sendATcommand("AT+FTPPUT=2,0", "OK", 30000);
            }
        }
        else
        {
            sendATcommand("AT+FTPPUT=2,0", "OK", 30000);
        }
    }
    else
    {
        Serial.println("Error openning the FTP session");
    }
}

El problema que yo uso una base de datos MySQL en una Raspberry Pi 3. Mi duda es que diferencia hay entre un servidor FTP y una base de datos MySQL. Yo para enviar archivos a MySQL normalmente lo hago desde algun script php que introduzca los archivos en las bases de datos. El tema de servidor FTP lo desconozco totalmente.

Vale, he leído un poco y se puede hacer. Habrá que instalar el servidor FTP en la Pi y luego unirlo con el servidor MySQL para poder mostrar imágenes en la pagina web.

Adjunto los links para que les echéis un ojo y me digáis si estoy o no en lo cierto.

http://movilforum.com/instalar-servidor-ftp-raspberry/

http://morelosgeek.com/2014/02/instalar-apache-mysql-y-ftp-en-raspberry/

lo que no entiendo es si vas a mandar mas status de variables o textos para alimentar a la BD so si solo son las imagenes,

si son solo imagenes solo recibelas con un server ftp como lo hace tu primer link (movilforum), si en el mismo raspberry esta el web server desde ahi las jalas para mostrarlas en linea con apache o lo que sea

yo hice hace mucho un sistema igual que era un timbre al cual al presionar tomaba una foto de quien lo toco y por serial y despues la enviaba a un server por GPRS y ftp (webcindario) que es totalmente gratis y ahi puedes interaccionar con las imagenes, solo gasté plata en la parte de la generacion de la foto, y nada en el server.

|500x375

Gracias por la información betomax.
No tendrás por ahí el Sketch que usaste? Más que nada por la parte de subir el archivo al servidor FTP.
Ya lo tengo instalado en la raspberry pi y funciona perfectamente, solo me falta saber como se envían las dichosas imágenes al FTP server desde arduino usando comando AT en el gprs shield.

Saludos.

Hola

no lo tengo a la mano, tiene algo de tiempo que no programo con Arduino , pero me basé en el sig.

http://playground.arduino.cc/Code/FTP

usé la primer version del sim900, dejame buscar en mis discos duros, si lo encuentro con todo gusto lo posteo

Betomax, es la 3ra o 4ta vez que veo que pones enlaces sin usar tags.
**Lee las normas del foro. **
Imagenes códigos y enlaces, todos van con tags según las normas.

Gracias betomax, le echaré un ojo.

surbyte: Betomax, es la 3ra o 4ta vez que veo que pones enlaces sin usar tags. Lee las normas del foro. Imagenes códigos y enlaces, todos van con tags según las normas.

arreglado, gracias