github.com/niedbalski/juju@v0.0.0-20190215020005-8ff100488e47/worker/uniter/runner/jujuc/status-get.go (about) 1 // Copyright 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package jujuc 5 6 import ( 7 "github.com/juju/cmd" 8 "github.com/juju/errors" 9 "github.com/juju/gnuflag" 10 11 jujucmd "github.com/juju/juju/cmd" 12 "github.com/juju/juju/core/status" 13 ) 14 15 // StatusGetCommand implements the status-get command. 16 type StatusGetCommand struct { 17 cmd.CommandBase 18 ctx Context 19 includeData bool 20 applicationWide bool 21 out cmd.Output 22 } 23 24 func NewStatusGetCommand(ctx Context) (cmd.Command, error) { 25 return &StatusGetCommand{ctx: ctx}, nil 26 } 27 28 func (c *StatusGetCommand) Info() *cmd.Info { 29 doc := ` 30 By default, only the status value is printed. 31 If the --include-data flag is passed, the associated data are printed also. 32 ` 33 return jujucmd.Info(&cmd.Info{ 34 Name: "status-get", 35 Args: "[--include-data] [--application]", 36 Purpose: "print status information", 37 Doc: doc, 38 }) 39 } 40 41 func (c *StatusGetCommand) SetFlags(f *gnuflag.FlagSet) { 42 c.out.AddFlags(f, "smart", cmd.DefaultFormatters) 43 f.BoolVar(&c.includeData, "include-data", false, "print all status data") 44 f.BoolVar(&c.applicationWide, "application", false, "print status for all units of this application if this unit is the leader") 45 } 46 47 func (c *StatusGetCommand) Init(args []string) error { 48 return cmd.CheckEmpty(args) 49 } 50 51 // StatusInfo is a record of the status information for a application or a unit's workload. 52 type StatusInfo struct { 53 Tag string 54 Status string 55 Info string 56 Data map[string]interface{} 57 } 58 59 // ApplicationStatusInfo holds StatusInfo for an Application and all its Units. 60 type ApplicationStatusInfo struct { 61 Application StatusInfo 62 Units []StatusInfo 63 } 64 65 func toDetails(info StatusInfo, includeData bool) map[string]interface{} { 66 details := make(map[string]interface{}) 67 details["status"] = info.Status 68 if includeData { 69 data := make(map[string]interface{}) 70 for k, v := range info.Data { 71 data[k] = v 72 } 73 details["status-data"] = data 74 details["message"] = info.Info 75 } 76 return details 77 } 78 79 func (c *StatusGetCommand) ApplicationStatus(ctx *cmd.Context) error { 80 applicationStatus, err := c.ctx.ApplicationStatus() 81 if err != nil { 82 if errors.IsNotImplemented(err) { 83 return c.out.Write(ctx, status.Unknown) 84 } 85 return errors.Annotatef(err, "finding application status") 86 } 87 if !c.includeData && c.out.Name() == "smart" { 88 return c.out.Write(ctx, applicationStatus.Application.Status) 89 } 90 statusDetails := make(map[string]interface{}) 91 details := toDetails(applicationStatus.Application, c.includeData) 92 93 units := make(map[string]interface{}, len(applicationStatus.Units)) 94 for _, unit := range applicationStatus.Units { 95 units[unit.Tag] = toDetails(unit, c.includeData) 96 } 97 details["units"] = units 98 statusDetails["application-status"] = details 99 c.out.Write(ctx, statusDetails) 100 101 return nil 102 103 } 104 105 func (c *StatusGetCommand) unitOrApplicationStatus(ctx *cmd.Context) error { 106 var err error 107 108 if c.applicationWide { 109 return c.ApplicationStatus(ctx) 110 } 111 112 unitStatus, err := c.ctx.UnitStatus() 113 if err != nil { 114 if errors.IsNotImplemented(err) { 115 return c.out.Write(ctx, status.Unknown) 116 } 117 return errors.Annotatef(err, "finding workload status") 118 } 119 if !c.includeData && c.out.Name() == "smart" { 120 return c.out.Write(ctx, unitStatus.Status) 121 } 122 c.out.Write(ctx, toDetails(*unitStatus, c.includeData)) 123 return nil 124 } 125 126 func (c *StatusGetCommand) Run(ctx *cmd.Context) error { 127 return c.unitOrApplicationStatus(ctx) 128 }