Click here to Skip to main content
15,885,876 members
Articles / Programming Languages / C#
Tip/Trick

FTP Upload/Download of Text Files in MetroApps

Rate me:
Please Sign up or sign in to vote.
4.60/5 (4 votes)
6 Aug 2013CPOL5 min read 15K   537   5   1
This shows how to use the new async logic to read/write, and upload/download text files in Metro apps.

Introduction

I am a basic meat and potatoes programmer, who is used to just surfing the net for the logic I need. But, I have spent an embarrassing long time trying to figure out how to upload and download text files to an FTP site for the new Metro Apps or Window Store app (whichever you prefer to call them). It seems to me that there is little on this subject out on the web. Since I have unraveled some of the mystery, I thought this may be the first time I am able to "play-it-forward" in thanks to all the years all of you in the development community have helped me out with your articles and responses to questions I leave in forums.

This downloaded project, will help anyone looking for logic code on simple read and write statements to/from a text file, but this information has been addressed well by others, the more important part of this code is the FTP upload/Download logic, which I have not found any decent Information on the internet about..

The code is simple and basic. It's only purpose is to give you building blocks to get started.

The FTP download is complete. There is a download for small files which is faster, but limited in size.. There is also a download for large files. The larger one will also processed the small files, but is slower to do so. It's power is with larger files where you can pause the download and restart the download, and it doesn't limit the size of the file.

The FTP upload is not complete. I have only found a way to do small files. This has a nice feature that you can process a small text file, or simply write data directly to the FTP site without need of creating a local text file. Unfortunately though it seems the logic used for the large downloads can be altered to be an upload, but when you try to process it, it informs you that it will only process HTTP sites.

I am open to any help from fellow developers who figure out how to upload a large data file, or can offer advice on how to improve and streamline my current code. I will be happy to give credit to any collaboration and help offered.

Using the code

The download contains four folders:

  • FTPFileProcessing - Metro App code
  • LocalFolder - Files for Local area processing
  • PackageAppSetup - Highlight of coding logic that you may miss when you attempt to recreate the logic in your own code
  • RemoteFolder - Files for FTP area processing

Before using the application, you need to do some setup:

  1. Create an FTP site with a folder named FTPFileProcessing.
  2. Move the Remotefolder into your FTPsites FTPFileProcessing folder.
  3. In your "My Documents" area, create a folder FTPFileProcessing. Into this folder, move the Localfolder that was in the zipped file.
  4. On the main page of the Metro app, you need to set ftpUriInfo, Username, and Password variables to match your newly created FTP area.
C#
public sealed partial class MainPage : Page
{
   //You need to set up your own ftp site and set ftpURIInof, Username & Password 

    //to it..
   string ftpURIInfo = ftp://999.999.999.999//FTPFileProcessing/RemoteFolder;
   string Username = "usrname";
   string Password = "pswd";
           :
           :

<project should now work>

Image 1

  • Button 1: Download Small Text file – move from FTP site to local computer
  • Button 2: Download Large Text file – move from FTP site to local computer

  • Button 3: Download Unknown sized Text file – Figures out size of file in FTP area, then choose either to use the small download logic or the large download logic.

  • Button 4: Create Text file in Remote Area – Create a text file in the FTP area, and write the data directly into that file.

  • Button 5: Large TextFile Upload, but this does not work for FTP, it will only work for http.. So the logic is
    commented out.

  • Button 6: Small TextFile Read/Upload – move a small text file from Local area to the FTP site.

  • Button 7: TextFile Write/Read – Writing and reading Text files into a local area.

  • Button 8: Delimited TextFile Write/Read – Working with a delimited Text file. Moving the data from array fields into named fields..

  • Button 9: Delete Remote file

  • Button 10: Get Remote file details – Reading a file to find out the size, Creation Date and filename.

  • Button 11: Delete local file

Points of Interest

There is a lot within the code. So I am just going to highlight some of it.

First. In order to work with local Text files and FTP sites you must set up to get permissions within your code. This is done in the package.appxmanifest.

Under the capabilities tab, you must set up for being able to work with the my Documents folder for local text files, and also the ability to work with Private networks (Client & Server) to work with FTP.

Image 2

Under the Declarations Tab, you must set up a file type association for txt files.

Image 3

Button2: Code for Large Downloads (from FTP to Local documents area)

Calling subroutine: (need to pass the parameters, even though they are set to be seen throughout the class, because static keyword in the LargeDownLoad method prevents the method from recognizing any varibles outside of itself.

C#
Successful = await LargeDownLoad(localsubfolders, ftpURIInfo, 
          Username, Password, filename);

LargeDownLoad subroutine: This is a BackgroundDownloader.. The local file points to the Documents Library, to have it go outside of the KnownFolders area for Documents, you would need to add a picker, and prompt the user where they want it every time the file downloads.. For routine downloads that you want to automatically do without the user being involved the only choice is the knownfolders area..

Credentials are needed for FTP to add the username & password

C#
public static async Task<bool> LargeDownLoad(string localsubfolders, 
       string ftpURIInfo, string Username, string Password, string filename)
{
    bool Successful = false;

    try
    {
        StorageFolder localFolderArea;
        BackgroundDownloader downloader = new BackgroundDownloader();
        localFolderArea = await KnownFolders.DocumentsLibrary.CreateFolderAsync(
            localsubfolders, CreationCollisionOption.OpenIfExists);

        StorageFile localFilePath = await localFolderArea.CreateFileAsync(
            filename, CreationCollisionOption.ReplaceExisting);

        Uri urlWithCredential;
        bool Success = Uri.TryCreate(ftpURIInfo + "/" + 
               filename, UriKind.Absolute, out urlWithCredential);
        urlWithCredential = new Uri(urlWithCredential.ToString().ToLower().Replace(@"ftp://")
        string.Format(@"ftp://{0}:{1}@",Username, Password)));
        DownloadOperation download = downloader.CreateDownload(urlWithCredential, localFilePath);
        await download.StartAsync();
        Successful = true;
    }
    catch (Exception)
    {
        throw;
    }
    return Successful;
}

Button 6: Small TextFile Read/Upload

Calling statements:

C#
string[] data1 = await ReadFile(localsubfolders, filename, "FullText");
Successful = await SmallUpload(ftpURIInfo, filename, Username, Password, data1[0]);

Subroutine ReadFile: This is only a small download as it is limited to the amount of data a string line can hold. first you need to read the local file and pickup the data in the file..

public static async Task<string[]> ReadFile(string localSubFolders, string filename, string ReadType)
{
   // Now rather then create a file same command now finds the file???
   string[] datalines = new string[1];
   try
   {
     StorageFolder storageFolder = 
       await KnownFolders.DocumentsLibrary.CreateFolderAsync(localSubFolders, 
       CreationCollisionOption.OpenIfExists);
    StorageFile setfilename = await storageFolder.GetFileAsync(filename);
    if (ReadType == "SeprateLines")
    {
       // Read the data
       var alldata = await Windows.Storage.FileIO.ReadLinesAsync(setfilename);
      datalines = new string[alldata.Count];
      Int32 ko = 0;
      foreach (var line in alldata)
      {
          datalines[ko] = line.ToString();
          ko = ko + 1;
       }
   }
   else if (ReadType == "FullText")
   {
      datalines[0] = await Windows.Storage.FileIO.ReadTextAsync(setfilename);
    }
  }
  catch (FileNotFoundException)
  {
     throw;
  }

   return datalines;

}

Subroutine SmallUpload: After which you can move it to the upload routine and pass it to the FTP site. This is using the web request method..

C#
public static async Task<bool> SmallUpload(string ftpURIInfo, 
         string filename, string username, string password, string UploadLine)
{
  string serverUrl;
  Uri serverUri = null;
  NetworkCredential credential;
  bool Successful = false;
  try
  {
    Uri.TryCreate(ftpURIInfo, UriKind.Absolute, out serverUri);
    serverUrl = serverUri.ToString();
    credential = new System.Net.NetworkCredential(username.Trim(),
    password.Trim());

    WebRequest request = WebRequest.Create(serverUrl + "/" + filename);
   request.Credentials = credential;
   request.Proxy = WebRequest.DefaultWebProxy;
    request.Method = "STOR";
    byte[] buffer = Encoding.UTF8.GetBytes(UploadLine)
    using (Stream requestStream = await request.GetRequestStreamAsync())
    {
         await requestStream.WriteAsync(buffer, 0, buffer.Length);
         await requestStream.FlushAsync()
     }
     Successful = true;
   }
   catch (Exception)
   {
      throw;
   }
   return Successful;
}

History

  • 8/6/2013 - Submitted the article.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
United States United States
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
QuestionGetting this below exception.. can you help ? Pin
rjrohit230318-Aug-16 8:57
rjrohit230318-Aug-16 8:57 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.