Home > Software Development, vSphere API > How to Download File from Guest Operating System on VMware

How to Download File from Guest Operating System on VMware

March 11th, 2012 Leave a comment Go to comments

In my last few posts I discussed how to use the Guest Operating System Management API to run program, set/read environment variables. From this post, I will talk about how to move files to and from a Guest Operating System, and advanced features like moving whole directory only implemented in the Guest Operating System Management API.

The vSphere API as of version 5.0 integrates VIX API. It provides basic APIs for downloading and uploading a file to a guest operating system. The basic idea is to use HTTPs protocol. When downloading a file from a guest operating system, the caller gets a URL which can be downloaded using GET method. You can even download it with a browser. To upload a file to a guest operating system, the caller gets a URL too, but has to be used with PUT method. How does ESXi move a file to and from a guest operating system? It’s transparent and we shouldn’t care.

Lost VMs or Containers? Too Many Consoles? Too Slow GUI? Time to learn how to "Google" and manage your VMware and clouds in a fast and secure HTML5 App.

There are more features provided by the vSphere API, for example, to create a temporary file, rename (in UNIX term, move) a file or directory, etc. These additional features can alternatively be implemented with running commands in the guest operating system. Again, you have to know the type of the guest operating system for a right command if you choose that way. This is really not a big deal because you have to provide operating sytem specific paths anyway.

Although the vSphere API works fine, I found it’s too low level, meaning you have to handle many details like URL, input and output stream, etc. Ideally, all that the caller should specify is: file path in a guest operating system, and local file path. That is exactly what I did in the guest operating system management API announced last week.

Let’s take a look at a sample code: (To run it, first check out the simple prerequisites in a previous post)

/*=============================================================================
Copyright (c) 2012 Steve Jin, All Rights Reserved.
http://www.doublecloud.org
=============================================================================*/

package org.doublecloud.vi.vmware.guest.samples;

import java.net.URL;

import org.doublecloud.vi.vmware.guest.GuestProcessDirector;

import com.vmware.vim25.mo.Folder;
import com.vmware.vim25.mo.InventoryNavigator;
import com.vmware.vim25.mo.ManagedEntity;
import com.vmware.vim25.mo.ServiceInstance;
import com.vmware.vim25.mo.VirtualMachine;

public class GuestDownloadFile
{
  public static void main(String[] args) throws Exception
  {
    ServiceInstance si = new ServiceInstance(new URL("https://8.8.8.8/sdk"), "Administrator", "doublecloud.org", true);
    Folder rootFolder = si.getRootFolder();

    ManagedEntity[] mes = new InventoryNavigator(rootFolder).searchManagedEntities("VirtualMachine");
    if (mes == null || mes.length == 0)
    {
      return;
    }

    VirtualMachine vm = (VirtualMachine) mes[0];

    System.out.println("guest tool status:" + vm.getGuest().toolsRunningStatus);
    if (!"guestToolsRunning".equals(vm.getGuest().toolsRunningStatus))
    {
      System.out.println("The VMware Tools is not running in the Guest OS on VM: " + vm.getName());
      System.out.println("Exiting...");
      return;
    }

    GuestFileDirector fd = new GuestFileDirector(vm, "Administrator", "vijava");

    fd.downloadFile("c:\\temp\\steveproxy.jar", "C:\\temp\\steveproxy.jar");
    fd.downloadDirectory("C:\\temp1\\download", "C:\\temp1\\download_dl");

    si.getServerConnection().logout();
  }
}

As you can see from the code, it downloads a file called “c:\\temp\\steveproxy.jar” (the vSphere Java code generator) in guest operating system to a local file with same name. Even better, it downloads a whole directory and its subdirectories recursively in a single call. This is not a feature in basic vSphere API but in the guest operating system management API. Note that if you archive a directory using zip/tar/gzip/7z at source and extract it at destination, the performance will be likely much better because of compression and reduced SSL session creation.

I know it could be confusing which parameter for what operating system. As a convention, the first parameter is always the source, and the second destination despite it is upload or download.

  1. Terry_Lei
    July 2nd, 2012 at 08:37 | #1

    Hi Steve,

    Thanks for your posting about download files/directory from the Guest OS.

    I reused your codes and test in Windows platfroms (the guest OS is Windows, the machine where to run the program is also in windows platform). I have successfully downloaded the files and directory.

    Then I move the program under the linux platfrom (where our scripts will be hosted), I was failed to download the directory:

    java.io.IOException: Server returned HTTP response code: 500 for URL:
    https://10.200.97.90:443/guestFile?id=45&token=52554745-8a6d-4d8f-b516-1458ebe439ca45
    at
    sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1612)
    at
    sun.net.www.protocol.https.HttpsURLConnectionImpl.getInputStream(HttpsURLConnectionImpl.java:254)
    at java.net.URL.openStream(URL.java:1035)
    at

    Have you gotten any idea?

    Thanks
    Terry

  2. Terry Lei
    July 2nd, 2012 at 09:54 | #2

    Hi Steve,

    Thanks for your posting, I reuse this codes, and test in Windows platform (The guest OS is Windows 7, the Os running the program is WinXP), it works! I successfully download the file and directory.

    Then I copy the program to linux platform (where our scripts will be hosted), I am failed to download the directory, I got HTTPs 500 errors. (As it is a server side error, so I guest there are some difference between the request sends from Linux platform and Windows platform).

    Have you got any idea about such issue?

    Thanks,
    Terry

  3. July 2nd, 2012 at 11:10 | #3

    Hi Terry,
    Thanks for reporting the success and issue. For the Linux VM, did you have VMware Tools installed? It’s required.
    Steve

  4. Terry_Lei
    July 2nd, 2012 at 21:09 | #4

    Hi Steve,

    Just when I run the program in Linux platform it will fail. (The guest OS is still Windows which has VM tools installed). Here is the exception I get:

    java.io.IOException: Server returned HTTP response code: 500 for URL:
    https://10.200.97.90:443/guestFile?id=45&token=52554745-8a6d-4d8f-b516-1458ebe439ca45
    at
    sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1612)
    at
    sun.net.www.protocol.https.HttpsURLConnectionImpl.getInputStream(HttpsURLConnectionImpl.java:254)
    at java.net.URL.openStream(URL.java:1035)
    at

  5. Terry Lei
    July 12th, 2012 at 22:33 | #5

    Hi Steve,

    Finally, I figure out the root case (sorry, I decode the vmguest.jar to peek into). When I use GuestFileDirector.uploadDirectory to upload the directory from Linux to Windows platform (download directory also has same issue), it will fail. The reason is, Linux uses “/” but windows use “\” as file separator. When uploading, I replace all the “/” in the path by “\\”, it works.

    Thanks for your tool, especially vijava, it is so great that help us to build our test tool very smoothly.

    -Terry

  6. July 17th, 2012 at 10:56 | #6

    Thanks for sharing your trick with the community Terry!
    -Steve

  7. Ramji
    August 23rd, 2013 at 07:42 | #7

    Hi,

    when i am trying upload or download from or to Guest Operating System.
    It is failing in vcenter 5.1 or the VM on host which is running on ESX5.1 version.

    It is working fine with 5.0 versions

    Can any please help how to solve this issue.

    Thanks,
    Ramji.

  8. August 23rd, 2013 at 16:41 | #8

    Hi Ramji,

    Do you have the updated VMware Tools installed in the VM?

    Steve

  9. Ramji
    August 26th, 2013 at 07:02 | #9

    Hi steve,

    Thanks for your reply.

    Actually we have upgraded VM Tools on the VM.

    VirtualMachine vm = validateEsx5AndVMTools(account, vms);

    if (vm != null)
    {
    GuestFileDirector fd = new GuestFileDirector(vm, vmUserName, vmPassword);
    }

    Here in the above code.

    It is validating validateEsx5AndVMTools it is validating correctly.

    but when it is going to GuestFileDirector class it is throwing Null Pointer Exception.

    Can you please help what went wrong for vcenter5.1 VMs with the above class

    Any specific things your are checking please let us know, so that we will pass accordingly.

    Thanks,
    Ramji.

  10. Pankaj
    October 16th, 2013 at 11:38 | #10

    Hi Steve,

    Your works are really helpful for us.
    Just Wanted to know, How can we know the return code and command output of any command when we run in Guest VM. ?

    If possible Can you post the example.

  11. October 16th, 2013 at 13:59 | #11

    Glad you like it. There is no direct way to return the output unfortunately.

    Steve

  12. Dan
    October 17th, 2013 at 07:22 | #12

    Hi Steve,

    We’re also getting the following IOException: Server returned HTTP response code: 500 for URL: https://10.151.101.102:443/guestFile?id=29&token=521ec9d1-a574-84b0-ab4b-db5bdf13c5e929

    This occurs intermittently while downloading files from a Linux vm to both Windows and Linux machines. The file separators are being set correctly – depending on the underlying OS. Any help ??

  13. October 17th, 2013 at 10:36 | #13

    Hi Dan,

    The HTTP 500 is internal server error which is a generic error message with no more specific details. The URL you presented seems good. Unless you can find an way to reproduce it, there is no much anyone can help. BTW, what version of the server?

    Steve

  14. Pankaj
    October 17th, 2013 at 12:20 | #14

    Thanks Steve for acknowledging. I am indirectly solving my purpose by redirecting output to file inside guest vm and then using GuestProcessInfo and FileTransferInformation for process execution status and reading the content of output file url.

    @Steve Jin

  15. Dan
    October 17th, 2013 at 12:38 | #15

    We are using Vcenter 5.5 (ESXi hosts 5.5) with VI Java 5.1. Unfortunately we haven’t found a way to replicate this yet.@Steve Jin

  16. October 17th, 2013 at 22:41 | #16

    That is cool. Thanks for sharing!

    Steve

  17. October 17th, 2013 at 22:43 | #17

    Thanks for the update. BTW, VI Java 5.5 beta is ready and you may want to try it out soon.

    Steve

  18. December 11th, 2013 at 05:32 | #18

    Unable to find below class in vijava55b20130927.jar file, Please suggest

    org.doublecloud.vi.vmware.guest.GuestProcessDirector

  19. December 11th, 2013 at 05:36 | #19

    Hi steve,

    Please suggest correct .jar file containing “org.doublecloud.vi.vmware.guest.GuestProcessDirector” class

  20. December 11th, 2013 at 14:55 | #20

    Hi Rosapanidu, The guest API is not open sourced with vijava API. Should you need it for your product or in house system, please ping me via email.

    Steve

  21. Chaithanya
    December 16th, 2013 at 09:56 | #21

    Hi Steve,

    I need the sources of vmguest.jar for debugging an issue.

    Am unable to create org.doublecloud.vi.vmware.guest.GuestProcessDirector object. It returns null pointer exception when I am trying to instantiate it as below

    GuestProcessDirector progDir = new GuestProcessDirector(vm, vmUserName, vmPassword);

    am passing constructor arguments as com.vmware.vim25.mo.VirtualMachine object followed by user name and password as string literals.

    where would be the problem? Any suggestions?

  22. Sameer Siddiqui
    August 25th, 2014 at 18:19 | #22

    Hello Steve,

    I’m very impressed with the VIJava API’s extremely helpful. One quick question is where can I download vmguest.jar file so I can try out your samples

    Thank You so much for your great contribution

    Sameer

  1. March 12th, 2012 at 00:04 | #1