github.com/vmware/govmomi@v0.51.0/cli/datastore/download.go (about)

     1  // © Broadcom. All Rights Reserved.
     2  // The term “Broadcom” refers to Broadcom Inc. and/or its subsidiaries.
     3  // SPDX-License-Identifier: Apache-2.0
     4  
     5  package datastore
     6  
     7  import (
     8  	"context"
     9  	"errors"
    10  	"flag"
    11  	"fmt"
    12  	"io"
    13  	"os"
    14  	"path"
    15  
    16  	"github.com/vmware/govmomi/cli"
    17  	"github.com/vmware/govmomi/cli/flags"
    18  	"github.com/vmware/govmomi/object"
    19  	"github.com/vmware/govmomi/ovf"
    20  	"github.com/vmware/govmomi/vim25/soap"
    21  	"github.com/vmware/govmomi/vmdk"
    22  )
    23  
    24  type download struct {
    25  	*flags.DatastoreFlag
    26  	*flags.HostSystemFlag
    27  }
    28  
    29  func init() {
    30  	cli.Register("datastore.download", &download{})
    31  }
    32  
    33  func (cmd *download) Register(ctx context.Context, f *flag.FlagSet) {
    34  	cmd.DatastoreFlag, ctx = flags.NewDatastoreFlag(ctx)
    35  	cmd.DatastoreFlag.Register(ctx, f)
    36  
    37  	cmd.HostSystemFlag, ctx = flags.NewHostSystemFlag(ctx)
    38  	cmd.HostSystemFlag.Register(ctx, f)
    39  }
    40  
    41  func (cmd *download) Process(ctx context.Context) error {
    42  	if err := cmd.DatastoreFlag.Process(ctx); err != nil {
    43  		return err
    44  	}
    45  	if err := cmd.HostSystemFlag.Process(ctx); err != nil {
    46  		return err
    47  	}
    48  	return nil
    49  }
    50  
    51  func (cmd *download) Usage() string {
    52  	return "SOURCE DEST"
    53  }
    54  
    55  func (cmd *download) Description() string {
    56  	return `Copy SOURCE from DS to DEST on the local system.
    57  
    58  If DEST name is "-", source is written to stdout.
    59  
    60  Examples:
    61    govc datastore.download vm-name/vmware.log ./local.log
    62    govc datastore.download vm-name/vmware.log - | grep -i error
    63    govc datastore.download -json vm-name/vm-name.vmdk - | jq .ddb
    64    ovf=$(govc library.info -l -L vmservice/photon-5.0/*.ovf)
    65    govc datastore.download -json "$ovf" - | jq -r .diskSection.disk[].capacity`
    66  }
    67  
    68  func (cmd *download) Run(ctx context.Context, f *flag.FlagSet) error {
    69  	args := f.Args()
    70  	if len(args) != 2 {
    71  		return errors.New("invalid arguments")
    72  	}
    73  
    74  	src := args[0]
    75  	dst := args[1]
    76  
    77  	var dp object.DatastorePath
    78  	if dp.FromString(src) {
    79  		// e.g. `govc library.info -l -L ...`
    80  		cmd.DatastoreFlag.Name = dp.Datastore
    81  		src = dp.Path
    82  	}
    83  
    84  	ds, err := cmd.Datastore()
    85  	if err != nil {
    86  		return err
    87  	}
    88  
    89  	h, err := cmd.HostSystemIfSpecified()
    90  	if err != nil {
    91  		return err
    92  	}
    93  
    94  	var via string
    95  
    96  	if h != nil {
    97  		via = fmt.Sprintf(" via %s", h.InventoryPath)
    98  		ctx = ds.HostContext(ctx, h)
    99  	}
   100  
   101  	p := soap.DefaultDownload
   102  
   103  	if dst == "-" {
   104  		f, _, err := ds.Download(ctx, src, &p)
   105  		if err != nil {
   106  			return err
   107  		}
   108  
   109  		if cmd.DatastoreFlag.All() {
   110  			switch path.Ext(src) {
   111  			case ".vmdk":
   112  				data, err := vmdk.ParseDescriptor(f)
   113  				if err != nil {
   114  					return err
   115  				}
   116  				return cmd.DatastoreFlag.WriteResult(data)
   117  			case ".ovf":
   118  				data, err := ovf.Unmarshal(f)
   119  				if err != nil {
   120  					return err
   121  				}
   122  				return cmd.DatastoreFlag.WriteResult(data)
   123  			}
   124  		}
   125  
   126  		_, err = io.Copy(os.Stdout, f)
   127  		return err
   128  	}
   129  
   130  	if cmd.DatastoreFlag.OutputFlag.TTY {
   131  		logger := cmd.DatastoreFlag.ProgressLogger(fmt.Sprintf("Downloading%s... ", via))
   132  		p.Progress = logger
   133  		defer logger.Wait()
   134  	}
   135  
   136  	return ds.DownloadFile(ctx, src, dst, &p)
   137  }