Added a stubbed out logs command

pull/2342/head
John Welsh 9 years ago
parent 24d5b30856
commit b1fbc391ed

@ -134,6 +134,7 @@ func newRootCmd(out io.Writer) *cobra.Command {
addFlagsTLS(newHistoryCmd(nil, out)), addFlagsTLS(newHistoryCmd(nil, out)),
addFlagsTLS(newInstallCmd(nil, out)), addFlagsTLS(newInstallCmd(nil, out)),
addFlagsTLS(newListCmd(nil, out)), addFlagsTLS(newListCmd(nil, out)),
addFlagsTLS(newLogsCmd(nil, out)),
addFlagsTLS(newRollbackCmd(nil, out)), addFlagsTLS(newRollbackCmd(nil, out)),
addFlagsTLS(newStatusCmd(nil, out)), addFlagsTLS(newStatusCmd(nil, out)),
addFlagsTLS(newUpgradeCmd(nil, out)), addFlagsTLS(newUpgradeCmd(nil, out)),

@ -17,118 +17,69 @@ limitations under the License.
package main package main
import ( import (
"fmt"
"io" "io"
"regexp"
"text/tabwriter"
"github.com/gosuri/uitable"
"github.com/gosuri/uitable/util/strutil"
"github.com/spf13/cobra" "github.com/spf13/cobra"
"k8s.io/helm/pkg/helm" "k8s.io/helm/pkg/helm"
"k8s.io/helm/pkg/proto/hapi/release" "fmt"
"k8s.io/helm/pkg/proto/hapi/services"
"k8s.io/helm/pkg/timeconv"
) )
var statusHelp = ` var logsHelp = `
This command shows the status of a named release. This command gets logs for a named release
The status consists of:
- last deployment time
- k8s namespace in which the release lives
- state of the release (can be: UNKNOWN, DEPLOYED, DELETED, SUPERSEDED, FAILED or DELETING)
- list of resources that this release consists of, sorted by kind
- details on last test suite run, if applicable
- additional notes provided by the chart
` `
type statusCmd struct { type logsCmd struct {
release string release string
out io.Writer out io.Writer
client helm.Interface client helm.Interface
version int32 version int32
} }
func newStatusCmd(client helm.Interface, out io.Writer) *cobra.Command { func newLogsCmd(client helm.Interface, out io.Writer) *cobra.Command {
status := &statusCmd{ logs := &logsCmd{
out: out, out: out,
client: client, client: client,
} }
cmd := &cobra.Command{ cmd := &cobra.Command{
Use: "status [flags] RELEASE_NAME", Use: "logs [flags] RELEASE_NAME",
Short: "displays the status of the named release", Short: "Streams logs for the given release",
Long: statusHelp, Long: logsHelp,
PersistentPreRunE: setupConnection, PersistentPreRunE: setupConnection,
RunE: func(cmd *cobra.Command, args []string) error { RunE: func(cmd *cobra.Command, args []string) error {
if len(args) == 0 { if len(args) == 0 {
return errReleaseRequired return errReleaseRequired
} }
status.release = args[0] logs.release = args[0]
if status.client == nil { if logs.client == nil {
status.client = helm.NewClient(helm.Host(settings.TillerHost)) logs.client = helm.NewClient(helm.Host(settings.TillerHost))
} }
return status.run() return logs.run()
}, },
} }
cmd.PersistentFlags().Int32Var(&status.version, "revision", 0, "if set, display the status of the named release with revision")
return cmd return cmd
} }
func (s *statusCmd) run() error { func (l *logsCmd) run() error {
res, err := s.client.ReleaseStatus(s.release, helm.StatusReleaseVersion(s.version)) done := make(chan struct{})
if err != nil { stream, err := l.client.ReleaseLogs(l.release, done)
return prettyError(err)
}
PrintStatus(s.out, res) fmt.Println("Listening for logs")
for {
select {
case l, ok := <-stream:
if !ok {
return nil return nil
} }
fmt.Println(l)
// PrintStatus prints out the status of a release. Shared because also used by
// install / upgrade
func PrintStatus(out io.Writer, res *services.GetReleaseStatusResponse) {
if res.Info.LastDeployed != nil {
fmt.Fprintf(out, "LAST DEPLOYED: %s\n", timeconv.String(res.Info.LastDeployed))
} }
fmt.Fprintf(out, "NAMESPACE: %s\n", res.Namespace)
fmt.Fprintf(out, "STATUS: %s\n", res.Info.Status.Code)
fmt.Fprintf(out, "\n")
if len(res.Info.Status.Resources) > 0 {
re := regexp.MustCompile(" +")
w := tabwriter.NewWriter(out, 0, 0, 2, ' ', tabwriter.TabIndent)
fmt.Fprintf(w, "RESOURCES:\n%s\n", re.ReplaceAllString(res.Info.Status.Resources, "\t"))
w.Flush()
}
if res.Info.Status.LastTestSuiteRun != nil {
lastRun := res.Info.Status.LastTestSuiteRun
fmt.Fprintf(out, "TEST SUITE:\n%s\n%s\n\n%s\n",
fmt.Sprintf("Last Started: %s", timeconv.String(lastRun.StartedAt)),
fmt.Sprintf("Last Completed: %s", timeconv.String(lastRun.CompletedAt)),
formatTestResults(lastRun.Results))
} }
if len(res.Info.Status.Notes) > 0 { if err != nil {
fmt.Fprintf(out, "NOTES:\n%s\n", res.Info.Status.Notes) return prettyError(err)
}
} }
func formatTestResults(results []*release.TestRun) string { return nil
tbl := uitable.New()
tbl.MaxColWidth = 50
tbl.AddRow("TEST", "STATUS", "INFO", "STARTED", "COMPLETED")
for i := 0; i < len(results); i++ {
r := results[i]
n := r.Name
s := strutil.PadRight(r.Status.String(), 10, ' ')
i := r.Info
ts := timeconv.String(r.StartedAt)
tc := timeconv.String(r.CompletedAt)
tbl.AddRow(n, s, i, ts, tc)
}
return tbl.String()
} }

@ -404,8 +404,7 @@ func (h *Client) logs(ctx context.Context, req *rls.GetReleaseLogsRequest, done
defer close(out) defer close(out)
defer c.Close() defer c.Close()
for { for {
select { rs, err := s.Recv()
case rs := s.Recv():
if err == io.EOF { if err == io.EOF {
return return
} }
@ -414,9 +413,19 @@ func (h *Client) logs(ctx context.Context, req *rls.GetReleaseLogsRequest, done
return return
} }
out <- rs out <- rs
case <-done: //select {
return ////case rs, err := s.Recv():
} //// if err == io.EOF {
//// return
//// }
//// if err != nil {
//// fmt.Println("gRPC error streaming logs: ", grpc.ErrorDesc(err))
//// return
//// }
//// out <- rs
//case <-done:
// return
//}
} }
}() }()

@ -42,6 +42,8 @@ import (
"k8s.io/helm/pkg/tiller/environment" "k8s.io/helm/pkg/tiller/environment"
"k8s.io/helm/pkg/timeconv" "k8s.io/helm/pkg/timeconv"
"k8s.io/helm/pkg/version" "k8s.io/helm/pkg/version"
"k8s.io/helm/pkg/tiller/logdistributor"
"time"
) )
// releaseNameMaxLen is the maximum length of a release name. // releaseNameMaxLen is the maximum length of a release name.
@ -84,6 +86,7 @@ var ValidName = regexp.MustCompile("^(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])+
type ReleaseServer struct { type ReleaseServer struct {
env *environment.Environment env *environment.Environment
clientset internalclientset.Interface clientset internalclientset.Interface
logs *logdistributor.Pubsub
} }
// NewReleaseServer creates a new release server. // NewReleaseServer creates a new release server.
@ -91,6 +94,7 @@ func NewReleaseServer(env *environment.Environment, clientset internalclientset.
return &ReleaseServer{ return &ReleaseServer{
env: env, env: env,
clientset: clientset, clientset: clientset,
logs: logdistributor.New(),
} }
} }
@ -281,6 +285,23 @@ func (s *ReleaseServer) GetReleaseContent(c ctx.Context, req *services.GetReleas
return &services.GetReleaseContentResponse{Release: rel}, err return &services.GetReleaseContentResponse{Release: rel}, err
} }
func (s *ReleaseServer) GetReleaseLogs(req *services.GetReleaseLogsRequest, stream services.ReleaseService_GetReleaseLogsServer) error {
t := time.NewTicker(time.Second)
//go func() {
for {
select {
case <-t.C:
fmt.Println("Sending a log")
stream.Send(&services.GetReleaseLogsResponse{Log: &release.Log{Log: "Test log!"}})
}
}
//}()
fmt.Println("Out of the for loop")
stream.Send(&services.GetReleaseLogsResponse{Log: &release.Log{Log: "Starting to stream logs!"}})
return nil
}
// UpdateRelease takes an existing release and new information, and upgrades the release. // UpdateRelease takes an existing release and new information, and upgrades the release.
func (s *ReleaseServer) UpdateRelease(c ctx.Context, req *services.UpdateReleaseRequest) (*services.UpdateReleaseResponse, error) { func (s *ReleaseServer) UpdateRelease(c ctx.Context, req *services.UpdateReleaseRequest) (*services.UpdateReleaseResponse, error) {
currentRelease, updatedRelease, err := s.prepareUpdate(req) currentRelease, updatedRelease, err := s.prepareUpdate(req)

Loading…
Cancel
Save