API to upload and extract ZIP

8 posts, 0 answers
  1. Andrew
    Andrew avatar
    3 posts
    Member since:
    May 2009

    Posted 13 Oct 2009 Link to this post

    Hi

    I would like to develop a module allowing admins to upload a zip file and extract the contents, in a similar way to the Sitefinity image/document library upload functionality. Is this zip & extract functionality available via an API, and are there any examples or documentation?

    A zip file will contain a Silverlight app and various media/resources referenced by that app (a zip may be 50Mb+ and contain hundreds of files and folders). Am I right in saying it wouldn't be practical to extract the zip to a Sitefinity library because the Silverlight app couldn't easily reference the files, also performance issues due to size and numbers? Would a better approach be to extract to the file system, and is this possible through the Sitefinity zip/extract API?

    Thanks in advance
    Andy
  2. Ivan Dimitrov
    Admin
    Ivan Dimitrov avatar
    78 posts

    Posted 13 Oct 2009 Link to this post

    Hello Andrew,

    You could upload Silverlight files to images and documents library of custom type where you do not have restriction about the extension of a file, but most probably the application will not work. The best way at this stage is uploading the application somewhere in your project - say in a root folder called SilverlightApplications.

    Is this zip & extract functionality available via an API, and are there any examples or documentation?

    Below is a sample code that illustrates using of ZipManager class.

    private void UploadFiles(ILibrary library)
     {
          
             foreach (UploadedFile file in RadUploadControl.UploadedFiles)
             {
     
                 ZipManager zipManager = new ZipManager();
                 IZipArchive zipArchive = zipManager.GetZipArchive(file.InputStream);
                 IAbstractFile[] archive = zipArchive.GetFiles(true);
     
                 long filesSize = 0;
                 if (library.MaxSize > 0)
                 {
                     foreach (IAbstractFile item in archive)
                     {
                         filesSize += item.Size;
                         if (filesSize > library.MaxSize)
                         {
                             HttpContext.Current.Response.Write("FILE SIZE PROBLEM");
                             return;
                         }
                     }
                 }
     
                 int i = -1;
                 foreach (IAbstractFile item in archive)
                 {
                     i++;
                     double percentIncrement = 100 / (double)archive.Length;
                     progress["PrimaryTotal"] = archive.Length.ToString();
                     if (i != 0)
                         progress["PrimaryPercent"] = ((int)(i * percentIncrement)).ToString();
                     progress["PrimaryValue"] = (i + 1).ToString();
     
                     string extension = String.Empty;
                     string name;
                     string itemName = item.FullName.Substring(item.RootFolder.FullName.Length - 1);
                     if (item.Name.LastIndexOf(".") != -1)
                     {
                         extension = item.Name.Substring(item.Name.LastIndexOf('.'));
                         name = item.Name.Remove(item.Name.LastIndexOf("."));
                     }
                     else
                         name = item.Name;
     
                     Stream str = item.OpenRead();
                     byte[] buffer = new byte[item.Size];
     
                     long position = 0;
                     int currentByte = str.ReadByte();
                     while (currentByte != -1)
                     {
                         buffer[position++] = (byte)currentByte;
                         currentByte = str.ReadByte();
                     }
                     try
                     {
                         this.manager = new LibraryManager();
                         // JUST FOR THE SAMPLE
                         //ILibrary lib = manager.GetLibrary("silverlight");
                         //or set it from the parameter.
                         itemId = manager.UploadFile(buffer,
                                                     name,
                                                     extension,
                                                     MimeMapper.GetMimeMapping(item.Name),
                                                     item.Size,
                                                     library).ID;
                         uploadedFileIDs.Add(itemId.ToString());
                     }
                     catch (ArgumentException)
                     {
                         FilesToUpload.Add(itemName, "NOT VALID");
                         continue;
                     }
                     catch (Exception)
                     {
                         FilesToUpload.Add(itemName, "UNKNOWN");
                         continue;
                     }
     
                     if (itemId != Guid.Empty)
                         FilesToUpload.Add(itemId.ToString(), "SUCCESSFULL");
                     else
                         FilesToUpload.Add(itemName, "UNKNOWN");
                 }
             }
             foreach (UploadedFile file in RadUploadControl.InvalidFiles)
             {
                 if (!file.GetExtension().Equals(".zip", StringComparison.OrdinalIgnoreCase))
                 {
                     HttpContext.Current.Response.Write("NOT VALID EXTENSION");
                     return;
                 }
             }
          
     }
     
     private LibraryManager manager;
     private List<string> uploadedFileIDs = new List<string>();
     private Guid itemId;
     // just for the the sample
     private RadUpload RadUploadControl;



    All the best,
    Ivan Dimitrov
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  3. DevCraft banner
  4. Andrew
    Andrew avatar
    3 posts
    Member since:
    May 2009

    Posted 13 Oct 2009 Link to this post

    Hi

    Thanks for the response. With your help I've created a user control that allows a user to upload a zip then unzip it to a folder. The user control contains a RadProgressArea, RadUpload and a button to start the upload/unzip operation. Just a couple of minor issues now, if you could assist please:-

    1) The RadProgressArea control is used to display progress during the file upload, and then during the unzip process (custom progress similar to your above code sample). Before the unzipping begins I want to change the progress area's Uploaded label to something more appropriate, e.g. "Unzipped:", so in my button click event I'm doing this:

    UploadedFile f = RadUploadContext.Current.UploadedFiles[0];  
     
    RadProgressArea1.Localization.Uploaded = "Unzipped: ";  
     
    UnzipFiles(f);  
                                     

    However the label never changes. Am I missing something? Is it something to do with AJAX/partial postbacks not updating the UI?

    2) On the RadProgressArea I have DisplayCancelButton=true. Do I need to handle any kind of cancel event or will the Cancel button stop any current operation itself (either a file upload or unzipping)? (It's just that I've noticed after clicking Cancel that the w3wp memory usage stays high, so I don't know if it is carrying on with the unzipping, or it's just the GC kicking in).

    Thanks again
    Andy
  5. Ivan Dimitrov
    Admin
    Ivan Dimitrov avatar
    78 posts

    Posted 13 Oct 2009 Link to this post

    Hi Andrew,

    Below is a sample implementation of the desired functionality

    protected void Page_Load(object sender, EventArgs e)
      {

          if (!IsPostBack)
          {
              RadProgressArea1.Localization.UploadedFiles = "Unzipped: ";
          }
          Button1.Click += new EventHandler(Button1_Click);
      }
     
      void Button1_Click(object sender, EventArgs e)
      {
          Telerik.Web.UI.RadProgressContext ProgressContex = Telerik.Web.UI.RadProgressContext.Current;
          ProgressContex.SecondaryTotal = "100";
          for (int i = 1; i < 100; i++)
          {
              ProgressContex.CurrentOperationText = "Uploading zip file percentage " + i.ToString();
                  // FORCE STOP UPLOADING
              if (!Response.IsClientConnected)
              {
                  break;
              }
              // SIMULATE TIME UPLOADING
              System.Threading.Thread.Sleep(100);
          }
      }
     
    <telerik:RadUpload id="RadUpload1" runat="server" OverwriteExistingFiles ="true"TargetFolder="~/Files" />
    <telerik:RadProgressManager ID="RadProgressManager1" runat="server" />
    <telerik:RadProgressArea
     ID="RadProgressArea1"
     runat="server"
     DisplayCancelButton="True"
     ProgressIndicators="FilesCountBar,
     FilesCount,
     FilesCountPercent,
     SelectedFilesCount,
     CurrentFileName,
     TimeElapsed,
     TimeEstimated">
    </telerik:RadProgressArea>
    <asp:Button ID="Button1" runat="server" Text="Unzip selected file" />


    You can modify the code and integrate it with the previous solution I sent.

    Sincerely yours,
    Ivan Dimitrov
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  6. Andrew
    Andrew avatar
    3 posts
    Member since:
    May 2009

    Posted 13 Oct 2009 Link to this post

    Hi

    Thanks again for the quick reply.

    I can also set the Localization properties in Page Load, but I need to do this in the button click event. I would like the text to be different during the file upload and during the unzipping, hence needing to do this in the button click event as per my earlier sample.

    It's not a big deal if this isn't possible, as I'll just use more generic text such as "Processed:".

    Thanks
    Andy
  7. Ivan Dimitrov
    Admin
    Ivan Dimitrov avatar
    78 posts

    Posted 13 Oct 2009 Link to this post

    Hi Andrew,

    You can modify the button click event as below.

    void Button1_Click(object sender, EventArgs e)
     {
         Telerik.Web.UI.RadProgressContext ProgressContex = Telerik.Web.UI.RadProgressContext.Current;
         ProgressContex.SecondaryTotal = "100";
         for (int i = 1; i < 100; i++)
         {
             foreach(UploadedFile file in RadUpload1.UploadedFiles)
             {
                 string ext = file.GetExtension();
                   if(ext == ".zip")
                   {
                     RadProgressArea1.Localization.UploadedFiles = "Unzipping: ";
                   }
                   else
                   {
                       RadProgressArea1.Localization.UploadedFiles = "Uploading: ";
                   }
             ProgressContex.CurrentOperationText = "Uploading zip file percentage " + i.ToString();
             // FORCE STOP UPLOADING
             if (!Response.IsClientConnected)
             {
                 break;
             }
             // SIMULATE TIME UPLOADING
             System.Threading.Thread.Sleep(100);
             }
         }
     }

    you can use switch loop. Note that the page should be refreshed because on each upload the control generates RadUrid = "some guid here"

    Regards,
    Ivan Dimitrov
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  8. Yusuf
    Yusuf avatar
    1 posts
    Member since:
    Nov 2011

    Posted 21 Nov 2011 Link to this post

    Hello Ivan

    I need to do the same operation using Silverlight RADUpload control and RADUploadHandler. I need to first Extract Zip files and show within the RADUpload Listbox and only upload the extracted files rather than the zip file to the Server location. I am able to extract the files using the code given in this link but cannot add it to the RADUpload listboxitem control.
    http://www.sharpgis.net/post/2009/04/22/REALLY-small-unzip-utility-for-Silverlight.aspx

    Any help on this regards would be much appreciated.

    Thanks & Regards
    Yusuf Shabbir
  9. Tina Stancheva
    Admin
    Tina Stancheva avatar
    3298 posts

    Posted 24 Nov 2011 Link to this post

    Hello Yusuf,

    Please have a look at this CodeLibrary solution and let us know if this is what you had in mind.

    Regards,
    Tina Stancheva
    the Telerik team

    Explore the entire Telerik portfolio by downloading the Ultimate Collection trial package. Get it now >>

Back to Top
DevCraft banner