Pages: [1]   Go Down
Author Topic: [Ethernet + SD] Download zip files from SD  (Read 2685 times)
0 Members and 1 Guest are viewing this topic.
Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I'm making a website with ethernet shield.

I wanted to click a link, and download a file from the memory card. Example: zip file

Click a link and do a task I know, I just wanted the part of the SD.

Anybody can help me?
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

and files *.txt, its possible?


 smiley-roll-sweat sorry for double post.
Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
I'm making a website with ethernet shield.
That's possible.

Quote
I wanted to click a link
Your web page, provided by the Arduino, needs to contain links. Does it? What does the Arduino do when a link is selected?

Quote
Example: zip file
What is the browser going to do with a zip file?

Quote
Click a link and do a task I know,
You haven't demonstrated this.

Quote
I just wanted the part of the SD.
The SD library comes with examples for listing the files on an SD card, and for reading from an SD card. Combining the relevant example with the web server code should be trivial. Read from a file and write to the client. Nothing really to it.
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

What is the browser going to do with a zip file?

The browser download the file to PC

You haven't demonstrated this.

The code:
Code:
EthernetClient client = server.available();
  if (client) {
    Serial1.println(F("new client"));
    // an http request ends with a blank line
    boolean currentLineIsBlank = true;
    String vars;

    int varDL=0;
    int dlaio=0;

    while (client.connected()) {
      if (client.available()) {
        char c = client.read();
        Serial1.write(c);
        vars.concat(c);

        if (vars.endsWith("=Download"))
        {
          varDL=1;
        }
        else if (vars.endsWith("/download/arduinoIO"))
        {
          varDL=1;
          dlaio=1;
        }

if (c == '\n' && currentLineIsBlank) {
          client.println(F("HTTP/1.1 200 OK"));
          client.println(F("Content-Type: text/html"));
          client.println(F("Connnection: close"));
          client.println();
          client.println(F("<!DOCTYPE HTML>"));
          client.println(F("<html>"));
          client.println(F("<head>"));
          // meta tag -> Faz refresh ao browser de 2 em 2 segundos
          client.println(F("<meta http-equiv=\"refresh\" content=\"2\">"));

(...)

if (varDL==1) // DOWNLOAD CENTER
          {
            client.println(F("<h1>Downloads</h1>"));
            client.println(F("<a href='/download/arduinoIO'>Matlab Support Package for Arduino (Arduino IO)</a>"));
          }
if (dlaio==1) // DOWNLOAD ARDUINO IO
          {
           //CODE FOR DOWNLOAD FILE
          }

(...)


The SD library comes with examples for listing the files on an SD card, and for reading from an SD card. Combining the relevant example with the web server code should be trivial. Read from a file and write to the client. Nothing really to it.
But the library only read/write txt files.
« Last Edit: July 01, 2012, 04:56:55 pm by bl0w » Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
But the library only read/write txt files.
The examples only show how to read/write text files, since they are the easiest to demonstrate proper functionality.

There is nothing in the library that restricts it from operating on files with other extensions. Whether a file contains "text" or binary data depends on what you write to the file. Text IS binary data, after all.
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Code:
if (dlaio==1) // DOWNLOAD ARDUINO IO
          {
           myFile = SD.open("ArduinoIO.zip");
           if (myFile)
           {
             // read from the file until there's nothing else in it:
             while (myFile.available())
             {
               client.write(myFile.read());
             }
             // close the file:
             myFile.close();
           }
           else
           {
             // if the file didn't open, print an error:
             client.println("FILE NOT FIND");
           }
}


i do this: replace Serial.write(myFile.read()); for client.write(myFile.read()); and don't work



to tell the browser that arduino are writing an html page we do:
Code:
client.println(F("HTTP/1.1 200 OK"));
client.println(F("Content-Type: text/html"));

do we have to do a similar thing to another file type? how can I indicate this?

Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
do we have to do a similar thing to another file type?
Yes. The type follows the / (text/html --> text/zip).

Code:
               client.write(myFile.read());
You should look at the return type from myFile.read() and the expected input to client.write(). You will see that they don't match. An intermediate variable or an explicit cast may be required.
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

if i do this:

Code:
EthernetClient client = server.available();
  if (client) {
    Serial1.println(F("new client"));
    boolean currentLineIsBlank = true;
    String vars;

    int varDL=0;
    int dlaio=0;
    int html=1;
    int txt=0;
    int zip=0;
    int dltext=0;

if (vars.endsWith("=Download"))
        {
          varDL=1;
          dlaio=0;
          zip=0;
          html=1;
          dltext=0;
          txt=0;
        }
        else if (vars.endsWith("/download/ArduinoIO.zip"))
        {
          varDL=1;
          dlaio=1;
          zip=1;
          html=0;
          txt=0;
        }
        else if (vars.endsWith("/download/sensor.txt"))
        {
          varDL=1;
          dlaio=0;
          dltext=1;
          zip=0;
          html=0;
          txt=1;
        }

if (c == '\n' && currentLineIsBlank) {
          // Cliente terminou de comunicar e o arduino tem de enviar
          // o seguinte cabeçalho para o browser
          client.println(F("HTTP/1.1 200 OK"));
          if(html==1)
          {
          client.println(F("Content-Type: text/html"));
          }
          if(txt==1)
          {
            client.println(F("Content-Type: text/txt"));
          }
          if(zip==1)
          {
            client.println(F("Content-Type: text/zip"));
          }
          client.println(F("Connnection: close"));
          client.println();
         
          client.println(F("<!DOCTYPE HTML>"));
          client.println(F("<html>"));
          client.println(F("<head>"));
          client.println(F("<meta http-equiv=\"refresh\" content=\"2\">"));

(...)

if (varDL==1) // DOWNLOAD CENTER
          {
            client.println(F("<h1>Downloads</h1>"));
            client.println(F("<a href='/download/ArduinoIO.zip'>Matlab Support Package for Arduino (Arduino IO)</a>"));
            client.println(F("<a href='/download/sensor.txt'>TESTE</a>"));
          }
         
          if (dltext==1) // download sensor.txt
          {
            myFile = SD.open("sensor.txt");
            if (myFile)
            {
              while (myFile.available())
              {
                client.write(myFile.read());
              }
              myFile.close();
            }
            else
            {
              client.println("FILE NOT FIND");
            }
          }
         
          if (dlaio==1) // DOWNLOAD ARDUINO IO
          {
            myFile = SD.open("ArduinoIO.zip");
            if (myFile)
            {
              while (myFile.available())
              {
                client.write(myFile.read());
              }
              myFile.close();
            }
            else
            {
              client.println("FILE NOT FIND");
            }
          }
client.println(F("</body>"));
client.println(F("</html>"));

(...)

The result is this:

FOR ZIP FILE:


FOR TXT FILE:


in the case of. * txt file the true file is this:




I am not able to do that, anyone who knows can tell me?
Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Code:
                client.write(myFile.read());
myFile.read() returns an int. The data of interest is in the low order byte. You need to research what happens when you call client.write() with an int. It may be sending both the high order byte and the low order byte, which would definitely screw up the file as saved on the PC.

It is not really recommended that you do this. Create an intermediate variable of the correct type to hold the output of the read() method, then call the write() method with that variable.

The Content-Type record should contain application/zip, not text/zip (sorry about that).

You may need to use a "Content-Encoding" record, too.
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 11
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Maybe this:
Code:
char myStrings[];
File myFile;

//(...)

if (varDLtxt==1) // download sensor.txt
          {
            int i;
            myFile = SD.open("sensor.txt");
            if (myFile)
            {
              while (myFile.available())
              {
                i=0;
                myStrings[i]=myFile.read();
                i=i+1;
                client.write(myStrings);
              }
              myFile.close();
            }
            else
            {
              client.println("FILE NOT FIND");
            }
          }
//(...)

but we can't declare an array without size, right?


Edit: I test with char myStrings[100];
Now appears the right values on page, but don't download.

« Last Edit: July 02, 2012, 01:06:00 pm by bl0w » Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 1
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Hi,

I don't know that the case is still open but I could make the zip download with the following code:

Code:
              client.println("HTTP/1.1 200 OK");
              client.println("Content-type: application/octet-stream");
              client.println("Content-disposition: attachment; filename=test.zip");
              //client.println("Connection: keep-alive");
              client.println();
                   File sensorFile = SD.open("test.zip");
                  if (sensorFile)
                  {
                    while (sensorFile.available())
                    {
                      client.write(sensorFile.read());
                    }
                    sensorFile.close();
                  }
                  else
                  {
                    client.println("FILE NOT FIND");
                  }
              }
Logged

Miramar Beach, Florida
Offline Offline
Faraday Member
**
Karma: 139
Posts: 5860
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

@TamasM:  You can greatly increase the speed by using a byte array to store a "packet", then send the array as one send. This is relatively slow compared to the buffered code. Here is the challenge:
Code:
     while (sensorFile.available())
       {
            client.write(sensorFile.read());
       }
It sends one byte per packet. Every call to client.write() generates a new packet.

Here is my server code running online. It uses a 64 byte array to buffer the data so it sends 64 bytes per packet.
http://68.99.58.119
http://forum.arduino.cc/index.php?topic=197103.0

Here is my code. It uploads about 4 times faster than your current code.
http://playground.arduino.cc/Code/WebServerST

edit: I did not include the ZIP file type in my original server code. I just added it.
« Last Edit: November 15, 2013, 07:25:39 am by SurferTim » Logged

Pages: [1]   Go Up
Jump to: